From b6fb35e68420b271824570094666628bd5a45fd3 Mon Sep 17 00:00:00 2001 From: Jason Fox Date: Fri, 31 May 2024 14:15:57 +0200 Subject: [PATCH] Remove tutorial from master --- .env | 25 - .gitpod.yml | 31 - ...erge-Patch and Put.postman_collection.json | 784 ----------- README.ja.md | 1178 ----------------- README.md | 1125 +--------------- data-models/alternate-context.jsonld | 283 ---- data-models/anomaly.jsonld | 35 - data-models/json-context.jsonld | 441 ------ data-models/ngsi-context.jsonld | 139 -- docker-compose/common.yml | 73 - docker-compose/orion-ld.yml | 39 - docker-compose/scorpio-aaio.yml | 85 -- docker-compose/stellio.yml | 107 -- docker-compose/stellio/kafka/update_run.sh | 11 - import-data | 107 -- services | 267 +--- 16 files changed, 11 insertions(+), 4719 deletions(-) delete mode 100644 .env delete mode 100644 .gitpod.yml delete mode 100644 NGSI-LD Merge-Patch and Put.postman_collection.json delete mode 100644 README.ja.md delete mode 100644 data-models/alternate-context.jsonld delete mode 100644 data-models/anomaly.jsonld delete mode 100644 data-models/json-context.jsonld delete mode 100644 data-models/ngsi-context.jsonld delete mode 100644 docker-compose/common.yml delete mode 100644 docker-compose/orion-ld.yml delete mode 100644 docker-compose/scorpio-aaio.yml delete mode 100644 docker-compose/stellio.yml delete mode 100755 docker-compose/stellio/kafka/update_run.sh delete mode 100644 import-data diff --git a/.env b/.env deleted file mode 100644 index 3e0f935..0000000 --- a/.env +++ /dev/null @@ -1,25 +0,0 @@ -# Project name -COMPOSE_PROJECT_NAME=fiware -EXPOSED_PORT=1026 - -# Orion variables -ORION_LD_PORT=1026 -ORION_LD_VERSION=1.3.0 - -# Scorpio variables -SCORPIO_PORT=9090 -SCORPIO_VERSION=4.1.1 - -# Stellio variables -STELLIO_DOCKER_TAG=2.5.2 -STELLIO_PORT=8080 -STELLIO_TIMESCALE_POSTGIS=14-2.11.1-3.3 - - -# MongoDB variables -MONGO_DB_PORT=27017 -MONGO_DB_VERSION=4.4 - -# Tutorial variables -TUTORIAL_APP_PORT=3000 -TUTORIAL_DUMMY_DEVICE_PORT=3001 diff --git a/.gitpod.yml b/.gitpod.yml deleted file mode 100644 index 14bd2a7..0000000 --- a/.gitpod.yml +++ /dev/null @@ -1,31 +0,0 @@ -tasks: - - name: Pull Images - init: ./services create - -ports: - - name: JSON-LD context (HTTPD) - description: Public User JSON-LD context - port: 3004 - onOpen: notify - visibility: public - - name: Context Broker - description: Context Broker - port: 1026 - onOpen: notify - visibility: public - - name: MongoDB - description: Database for Orion - port: 27017 - onOpen: ignore - - name: zookeeper - description: Synchronization service - port: 2181 - onOpen: ignore - - name: kafka - description: Stream-processing platform - port: 9092 - onOpen: ignore - - name: postgres - description: Database for Scorpio or Stellio - port: 5432 - onOpen: ignore \ No newline at end of file diff --git a/NGSI-LD Merge-Patch and Put.postman_collection.json b/NGSI-LD Merge-Patch and Put.postman_collection.json deleted file mode 100644 index 4eefbb5..0000000 --- a/NGSI-LD Merge-Patch and Put.postman_collection.json +++ /dev/null @@ -1,784 +0,0 @@ -{ - "info": { - "_postman_id": "a2eb08bc-bf13-40c9-bdbe-ec37f3f64f18", - "name": "NGSI-LD Merge-Patch and Put", - "schema": "https://schema.getpostman.com/json/collection/v2.1.0/collection.json", - "_exporter_id": "513743" - }, - "item": [ - { - "name": "Preflight", - "item": [ - { - "name": "Permitted options for entities", - "request": { - "method": "OPTIONS", - "header": [], - "url": { - "raw": "http://{{orion}}/ngsi-ld/v1/entities/", - "protocol": "http", - "host": [ - "{{orion}}" - ], - "path": [ - "ngsi-ld", - "v1", - "entities", - "" - ] - } - }, - "response": [] - }, - { - "name": "Permitted options for a single entity", - "request": { - "method": "OPTIONS", - "header": [], - "body": { - "mode": "raw", - "raw": "{\n \"temperature\":{\n \"coordinates\": [0,0]\n }\n}" - }, - "url": { - "raw": "http://{{orion}}/ngsi-ld/v1/entities/urn:ngsi-ld:City:001", - "protocol": "http", - "host": [ - "{{orion}}" - ], - "path": [ - "ngsi-ld", - "v1", - "entities", - "urn:ngsi-ld:City:001" - ] - } - }, - "response": [] - }, - { - "name": "Permitted options for entity attributes", - "request": { - "method": "OPTIONS", - "header": [], - "url": { - "raw": "http://{{orion}}/ngsi-ld/v1/entities/urn:ngsi-ld:City:001/attrs", - "protocol": "http", - "host": [ - "{{orion}}" - ], - "path": [ - "ngsi-ld", - "v1", - "entities", - "urn:ngsi-ld:City:001", - "attrs" - ] - } - }, - "response": [] - }, - { - "name": "Permitted options for an attribute", - "request": { - "method": "OPTIONS", - "header": [], - "url": { - "raw": "http://{{orion}}/ngsi-ld/v1/entities/urn:ngsi-ld:City:001/attrs/temperature", - "protocol": "http", - "host": [ - "{{orion}}" - ], - "path": [ - "ngsi-ld", - "v1", - "entities", - "urn:ngsi-ld:City:001", - "attrs", - "temperature" - ] - } - }, - "response": [] - } - ] - }, - { - "name": "Create,Read,Overwrite", - "item": [ - { - "name": "Create a New Data Entity (normalized)", - "request": { - "method": "POST", - "header": [ - { - "key": "Content-Type", - "value": "application/json" - }, - { - "key": "Link", - "value": "<{{ngsi-context.jsonld}}>; rel=\"http://www.w3.org/ns/json-ld#context\"; type=\"application/ld+json\"", - "type": "text" - }, - { - "key": "NGSILD-Tenant", - "value": "openiot", - "type": "text", - "disabled": true - } - ], - "body": { - "mode": "raw", - "raw": "{\n \"id\": \"urn:ngsi-ld:City:001\",\n \"type\": \"City\",\n \"temperature\": {\n \"type\": \"Property\",\n \"value\": 25,\n \"unitCode\": \"CEL\",\n \"observedAt\": \"2022-06-30T00:00:00.000Z\"\n },\n \"location\": {\n \"type\": \"GeoProperty\",\n \"value\": {\n \"type\": \"Point\",\n \"coordinates\": [\n 28.955,\n 41.0136\n ]\n }\n },\n \"population\": {\n \"type\": \"Property\",\n \"value\": 15840900,\n \"observedAt\": \"2022-12-31T00:00:00.000Z\"\n },\n \"address\": {\n \"type\": \"Property\",\n \"value\": {\n \"streetAddress\": \"Kanlıca İskele Meydanı\",\n \"addressRegion\": \"İstanbul\",\n \"addressLocality\": \"Beşiktaş\",\n \"postalCode\": \"12345\"\n }\n },\n \"name\": {\n \"type\": \"LanguageProperty\",\n \"languageMap\": {\n \"el\": \"Κωνσταντινούπολις\",\n \"en\": \"Constantinople\",\n \"tr\": \"İstanbul\"\n }\n },\n \"runBy\": {\n \"type\": \"Relationship\",\n \"object\": \"urn:ngsi-ld:Adminstration:001\"\n }\n}" - }, - "url": { - "raw": "http://{{orion}}/ngsi-ld/v1/entities/", - "protocol": "http", - "host": [ - "{{orion}}" - ], - "path": [ - "ngsi-ld", - "v1", - "entities", - "" - ] - } - }, - "response": [] - }, - { - "name": "Create a Second Data Entity (concise)", - "request": { - "method": "POST", - "header": [ - { - "key": "Content-Type", - "value": "application/json" - }, - { - "key": "Link", - "value": "<{{ngsi-context.jsonld}}>; rel=\"http://www.w3.org/ns/json-ld#context\"; type=\"application/ld+json\"", - "type": "text" - } - ], - "body": { - "mode": "raw", - "raw": "{\n \"id\": \"urn:ngsi-ld:City:002\",\n \"type\": \"City\",\n \"temperature\": {\n \"value\": 25,\n \"unitCode\": \"CEL\",\n \"observedAt\": \"2022-06-30T00:00:00.000Z\"\n },\n \"address\": {\n \"value\": {\n \"streetAddress\": \"Viale di Valle Aurelia\",\n \"addressRegion\": \"Lazio\",\n \"addressLocality\": \"Roma\",\n \"postalCode\": \"00138\"\n }\n },\n \"location\": {\n \"type\": \"Point\",\n \"coordinates\": [\n 12.482,\n 41.893\n ]\n },\n \"population\": {\n \"value\": 4342212,\n \"observedAt\": \"2021-01-01T00:00:00.000Z\"\n },\n \"name\": {\n \"languageMap\": {\n \"el\": \"Ρώμη\",\n \"en\": \"Rome\",\n \"it\": \"Roma\"\n }\n },\n \"runBy\": {\n \"object\": \"urn:ngsi-ld:Adminstration:001\"\n }\n}" - }, - "url": { - "raw": "http://{{orion}}/ngsi-ld/v1/entities/", - "protocol": "http", - "host": [ - "{{orion}}" - ], - "path": [ - "ngsi-ld", - "v1", - "entities", - "" - ] - } - }, - "response": [] - }, - { - "name": "Overwrite an Entity", - "request": { - "method": "PUT", - "header": [ - { - "key": "Content-Type", - "value": "application/json" - }, - { - "key": "Link", - "value": "<{{ngsi-context.jsonld}}>; rel=\"http://www.w3.org/ns/json-ld#context\"; type=\"application/ld+json\"", - "type": "text" - } - ], - "body": { - "mode": "raw", - "raw": "{\n\n \"type\": \"City\",\n \"temperature\": {\n \"type\": \"Property\",\n \"value\": 25,\n \"unitCode\": \"CEL\",\n \"observedAt\": \"2022-06-30T00:00:00.000Z\"\n },\n \"location\": {\n \"type\": \"Point\",\n \"coordinates\": [\n 12.482,\n 41.893 \n ]\n },\n \"name\": {\n \"type\": \"LanguageProperty\",\n \"languageMap\": {\n \"el\": \"Ρώμη\",\n \"en\": \"Rome\",\n \"it\": \"Roma\"\n }\n }\n}" - }, - "url": { - "raw": "http://{{orion}}/ngsi-ld/v1/entities/urn:ngsi-ld:City:002", - "protocol": "http", - "host": [ - "{{orion}}" - ], - "path": [ - "ngsi-ld", - "v1", - "entities", - "urn:ngsi-ld:City:002" - ] - } - }, - "response": [] - }, - { - "name": "Read a Data Entity (normalized)", - "request": { - "method": "GET", - "header": [ - { - "key": "Link", - "value": "<{{json-context.jsonld}}>; rel=\"http://www.w3.org/ns/json-ld#context\"; type=\"application/ld+json\"", - "type": "text" - }, - { - "key": "Accept", - "value": "application/json", - "type": "text", - "name": "Accept" - }, - { - "key": "NGSILD-Tenant", - "value": "openiot", - "type": "text", - "disabled": true - } - ], - "url": { - "raw": "http://{{orion}}/ngsi-ld/v1/entities/urn:ngsi-ld:City:001?options=normalized", - "protocol": "http", - "host": [ - "{{orion}}" - ], - "path": [ - "ngsi-ld", - "v1", - "entities", - "urn:ngsi-ld:City:001" - ], - "query": [ - { - "key": "options", - "value": "normalized", - "description": "* `keyValues` option in order to get a more compact and brief representation, including just attribute values\n* `values` option combined with a list of attribute values `attrs` for an ordered list of attributes only\n" - } - ] - } - }, - "response": [] - }, - { - "name": "Read a Data Entity (concise)", - "request": { - "method": "GET", - "header": [ - { - "key": "Link", - "value": "<{{json-context.jsonld}}>; rel=\"http://www.w3.org/ns/json-ld#context\"; type=\"application/ld+json\"", - "type": "text" - }, - { - "key": "Accept", - "value": "application/json", - "type": "text", - "name": "Accept" - }, - { - "key": "NGSILD-Tenant", - "value": "openiot", - "type": "text", - "disabled": true - } - ], - "url": { - "raw": "http://{{orion}}/ngsi-ld/v1/entities/urn:ngsi-ld:City:002/?options=concise", - "protocol": "http", - "host": [ - "{{orion}}" - ], - "path": [ - "ngsi-ld", - "v1", - "entities", - "urn:ngsi-ld:City:002", - "" - ], - "query": [ - { - "key": "options", - "value": "concise", - "description": "* `keyValues` option in order to get a more compact and brief representation, including just attribute values\n* `values` option combined with a list of attribute values `attrs` for an ordered list of attributes only\n" - }, - { - "key": "lang", - "value": "el", - "disabled": true - } - ] - } - }, - "response": [] - }, - { - "name": "Read a Data Entity (key-values)", - "request": { - "method": "GET", - "header": [ - { - "key": "Link", - "value": "<{{json-context.jsonld}}>; rel=\"http://www.w3.org/ns/json-ld#context\"; type=\"application/ld+json\"", - "type": "text" - }, - { - "key": "Accept", - "value": "application/json", - "type": "text", - "name": "Accept" - }, - { - "key": "NGSILD-Tenant", - "value": "openiot", - "type": "text", - "disabled": true - } - ], - "url": { - "raw": "http://{{orion}}/ngsi-ld/v1/entities/urn:ngsi-ld:City:001/?options=keyValues&lang=el", - "protocol": "http", - "host": [ - "{{orion}}" - ], - "path": [ - "ngsi-ld", - "v1", - "entities", - "urn:ngsi-ld:City:001", - "" - ], - "query": [ - { - "key": "options", - "value": "keyValues", - "description": "* `keyValues` option in order to get a more compact and brief representation, including just attribute values\n* `values` option combined with a list of attribute values `attrs` for an ordered list of attributes only\n" - }, - { - "key": "lang", - "value": "el" - } - ] - } - }, - "response": [] - } - ] - }, - { - "name": "Merge-Patch", - "item": [ - { - "name": "Merge-Patch Attributes", - "request": { - "method": "PATCH", - "header": [ - { - "key": "Link", - "value": "<{{ngsi-context.jsonld}}>; rel=\"http://www.w3.org/ns/json-ld#context\"; type=\"application/ld+json\"", - "type": "text" - } - ], - "body": { - "mode": "raw", - "raw": "{\n \"temperature\": 20,\n \"location\": {\n \"type\": \"Point\",\n \"coordinates\": [\n 13.3505,\n 52.5146\n ]\n }\n}", - "options": { - "raw": { - "language": "json" - } - } - }, - "url": { - "raw": "http://{{orion}}/ngsi-ld/v1/entities/urn:ngsi-ld:City:001", - "protocol": "http", - "host": [ - "{{orion}}" - ], - "path": [ - "ngsi-ld", - "v1", - "entities", - "urn:ngsi-ld:City:001" - ], - "query": [ - { - "key": "options", - "value": "keyValues", - "disabled": true - }, - { - "key": "attrs", - "value": "temperature", - "disabled": true - }, - { - "key": "", - "value": "", - "disabled": true - } - ] - } - }, - "response": [] - }, - { - "name": "Adding sub-attributes", - "request": { - "method": "PATCH", - "header": [ - { - "key": "Link", - "value": "<{{ngsi-context.jsonld}}>; rel=\"http://www.w3.org/ns/json-ld#context\"; type=\"application/ld+json\"", - "type": "text" - } - ], - "body": { - "mode": "raw", - "raw": "{\n \"temperature\": {\n \"type\": \"Property\",\n \"value\": 7,\n \"observedAt\": \"2022-03-14T12:51:02.000Z\",\n \"precision\": {\n \"value\": 0.95,\n \"unitCode\": \"C62\"\n }\n }\n}", - "options": { - "raw": { - "language": "json" - } - } - }, - "url": { - "raw": "http://{{orion}}/ngsi-ld/v1/entities/urn:ngsi-ld:City:001", - "protocol": "http", - "host": [ - "{{orion}}" - ], - "path": [ - "ngsi-ld", - "v1", - "entities", - "urn:ngsi-ld:City:001" - ], - "query": [ - { - "key": "options", - "value": "keyValues", - "disabled": true - }, - { - "key": "attrs", - "value": "temperature", - "disabled": true - }, - { - "key": "", - "value": null, - "disabled": true - } - ] - } - }, - "response": [] - }, - { - "name": "Using NGSI-LD null to delete", - "request": { - "method": "PATCH", - "header": [ - { - "key": "Link", - "value": "<{{ngsi-context.jsonld}}>; rel=\"http://www.w3.org/ns/json-ld#context\"; type=\"application/ld+json\"", - "type": "text" - } - ], - "body": { - "mode": "raw", - "raw": "{\n \"humidity\": 80,\n \"name\": {\n \"languageMap\": {\n \"el\": \"Βερολίνο\",\n \"en\": \"Berlin\",\n \"it\": \"Berlino\"\n }\n },\n \"temperature\": \"urn:ngsi-ld:null\"\n}", - "options": { - "raw": { - "language": "json" - } - } - }, - "url": { - "raw": "http://{{orion}}/ngsi-ld/v1/entities/urn:ngsi-ld:City:002", - "protocol": "http", - "host": [ - "{{orion}}" - ], - "path": [ - "ngsi-ld", - "v1", - "entities", - "urn:ngsi-ld:City:002" - ], - "query": [ - { - "key": "options", - "value": "keyValues", - "disabled": true - }, - { - "key": "attrs", - "value": "temperature", - "disabled": true - }, - { - "key": "", - "value": null, - "disabled": true - } - ] - } - }, - "response": [] - }, - { - "name": "Amending values of a Property with sub-attributes", - "request": { - "method": "PATCH", - "header": [ - { - "key": "Link", - "value": "<{{ngsi-context.jsonld}}>; rel=\"http://www.w3.org/ns/json-ld#context\"; type=\"application/ld+json\"", - "type": "text" - } - ], - "body": { - "mode": "raw", - "raw": "{\n \"address\": {\n \"value\": {\n \"addressLocality\": \"Fenerbahçe\",\n \"postalCode\": \"34567\"\n },\n \"verified\": \"true\"\n }\n}", - "options": { - "raw": { - "language": "json" - } - } - }, - "url": { - "raw": "http://{{orion}}/ngsi-ld/v1/entities/urn:ngsi-ld:City:001", - "protocol": "http", - "host": [ - "{{orion}}" - ], - "path": [ - "ngsi-ld", - "v1", - "entities", - "urn:ngsi-ld:City:001" - ], - "query": [ - { - "key": "attrs", - "value": "temperature", - "disabled": true - }, - { - "key": "", - "value": "", - "disabled": true - } - ] - } - }, - "response": [] - }, - { - "name": "Updating using key-values format", - "request": { - "method": "PATCH", - "header": [ - { - "key": "Link", - "value": "<{{ngsi-context.jsonld}}>; rel=\"http://www.w3.org/ns/json-ld#context\"; type=\"application/ld+json\"", - "type": "text" - } - ], - "body": { - "mode": "raw", - "raw": "{\n \"temperature\": 19,\n \"location\": {\n \"type\": \"Point\",\n \"coordinates\": [\n 13.3505,\n 52.5146\n ]\n },\n \"address\": {\n \"addressLocality\": \"Beyoğlu\",\n \"postalCode\": \"98765\"\n },\n \"runBy\": \"urn:ngsi-ld:Adminstration:Adalet_ve_Kalkınma_Partisi\"\n}", - "options": { - "raw": { - "language": "json" - } - } - }, - "url": { - "raw": "http://{{orion}}/ngsi-ld/v1/entities/urn:ngsi-ld:City:001?options=keyValues", - "protocol": "http", - "host": [ - "{{orion}}" - ], - "path": [ - "ngsi-ld", - "v1", - "entities", - "urn:ngsi-ld:City:001" - ], - "query": [ - { - "key": "attrs", - "value": "temperature", - "disabled": true - }, - { - "key": "", - "value": "", - "disabled": true - }, - { - "key": "options", - "value": "keyValues" - } - ] - } - }, - "response": [] - }, - { - "name": "Using key-values with observedAt", - "request": { - "method": "PATCH", - "header": [ - { - "key": "Link", - "value": "<{{ngsi-context.jsonld}}>; rel=\"http://www.w3.org/ns/json-ld#context\"; type=\"application/ld+json\"", - "type": "text" - } - ], - "body": { - "mode": "raw", - "raw": "{\n \"temperature\": 19,\n \"location\": {\n \"type\": \"Point\",\n \"coordinates\": [\n 13.3505,\n 52.5146\n ]\n }\n}", - "options": { - "raw": { - "language": "json" - } - } - }, - "url": { - "raw": "http://{{orion}}/ngsi-ld/v1/entities/urn:ngsi-ld:City:001?options=keyValues&observedAt=2022-10-10T10:10:00.000Z", - "protocol": "http", - "host": [ - "{{orion}}" - ], - "path": [ - "ngsi-ld", - "v1", - "entities", - "urn:ngsi-ld:City:001" - ], - "query": [ - { - "key": "options", - "value": "keyValues" - }, - { - "key": "attrs", - "value": "temperature", - "disabled": true - }, - { - "key": "", - "value": "", - "disabled": true - }, - { - "key": "observedAt", - "value": "2022-10-10T10:10:00.000Z" - } - ] - } - }, - "response": [] - }, - { - "name": "Using key-values with lang", - "request": { - "method": "PATCH", - "header": [ - { - "key": "Link", - "value": "<{{ngsi-context.jsonld}}>; rel=\"http://www.w3.org/ns/json-ld#context\"; type=\"application/ld+json\"", - "type": "text" - } - ], - "body": { - "mode": "raw", - "raw": "{\n \"temperature\": 19,\n \"population\": 15850000,\n \"name\": \"Istanbul, not Constantinople\"\n}", - "options": { - "raw": { - "language": "json" - } - } - }, - "url": { - "raw": "http://{{orion}}/ngsi-ld/v1/entities/urn:ngsi-ld:City:001?options=keyValues&lang=en", - "protocol": "http", - "host": [ - "{{orion}}" - ], - "path": [ - "ngsi-ld", - "v1", - "entities", - "urn:ngsi-ld:City:001" - ], - "query": [ - { - "key": "attrs", - "value": "temperature", - "disabled": true - }, - { - "key": "", - "value": "", - "disabled": true - }, - { - "key": "options", - "value": "keyValues" - }, - { - "key": "lang", - "value": "en" - } - ] - } - }, - "response": [] - } - ] - } - ], - "event": [ - { - "listen": "prerequest", - "script": { - "type": "text/javascript", - "exec": [ - "" - ] - } - }, - { - "listen": "test", - "script": { - "type": "text/javascript", - "exec": [ - "" - ] - } - } - ], - "variable": [ - { - "key": "orion", - "value": "localhost:1026", - "type": "string" - }, - { - "key": "ngsi-context.jsonld", - "value": "http://context/ngsi-context.jsonld", - "type": "string" - }, - { - "key": "json-context.jsonld", - "value": "http://context/json-context.jsonld", - "type": "string" - } - ] -} \ No newline at end of file diff --git a/README.ja.md b/README.ja.md deleted file mode 100644 index 10a747b..0000000 --- a/README.ja.md +++ /dev/null @@ -1,1178 +0,0 @@ -# Merge Patch NGSI-LD[](https://www.etsi.org/deliver/etsi_gs/CIM/001_099/009/01.06.01_60/gs_CIM009v010601p.pdf)[](https://www.fiware.org/)
- -[![FIWARE Core Context Management](https://nexus.lab.fiware.org/repository/raw/public/badges/chapters/core.svg)](https://github.com/FIWARE/catalogue/blob/master/core/README.md) -[![License: MIT](https://img.shields.io/github/license/fiware/tutorials.Merge-Patch-Put.svg)](https://opensource.org/licenses/MIT) -[![Support badge](https://img.shields.io/badge/tag-fiware-orange.svg?logo=stackoverflow)](https://stackoverflow.com/questions/tagged/fiware) -
[![JSON LD](https://img.shields.io/badge/JSON--LD-1.1-f06f38.svg)](https://w3c.github.io/json-ld-syntax/) -[![Documentation](https://img.shields.io/readthedocs/fiware-tutorials.svg)](https://fiware-tutorials.rtfd.io) - -このチュートリアルでは、NGSI-LD Merge Patch エンドポイントを紹介します。 マージ・パッチ (`/entities/`) -と部分更新パッチ (`/entities//attrs`) の違いを説明し、この機能の使用方法を示します。 - -チュートリアルでは全体で [cUrl](https://ec.haxx.se/) コマンドを使用していますが、 -[Postman documentation](https://fiware.github.io/tutorials.Merge-Patch-Put/ngsi-ld.html) -のドキュメントとしても利用できます。 - -[![Run in Postman](https://run.pstmn.io/button.svg)](https://app.getpostman.com/run-collection/d24facc3c430bb5d5aaf) - -## コンテンツ - -
-詳細 - -- [Merge-Patch と PUT](#merge-patch-and-put) - - [なぜ2種類の **PATCH** があるのか?](#why-two-kinds-of-patch-) - - [部分更新 **PATCH**](#partial-update-patch) - - [マージ **PATCH**](#merge-patch) - - [上書き **PUT**](#overwrite-put) -- [アーキテクチャ](#architecture) -- [前提条件](#prerequisites) - - [Docker と Docker Compose](#docker-and-docker-compose) - - [Cygwin for Windows](#cygwin-for-windows) -- [起動](#start-up) -- [マージ・パッチ操作](#merge-patch-operations) - - [プリフライト](#preflight) - - [Merge-Patch 操作](#merge-patch-operations-1) - - [マージ・パッチを使用した更新](#updating-using-merge-patch) - - [マージ・パッチを使用して新しい属性を追加](#adding-new-attributes-using-merge-patch) - - [マージ・パッチを使用して既存の属性を削除](#removing-existing-attributes-using-merge-patch) - - [サブ属性を使用してプロパティの値を修正](#amending-values-of-a-property-with-sub-attributes) - - [Key-Value フォーマットを使用した更新](#updating-using-key-values-format) - - [`observedAt` による Key-Value を使用した更新](#updating-using-key-values-with-observedat) - - [`lang` による Key-Value を使用した更新](#updating-using-key-values-with-lang) - - [**PUT** によるエンティティの上書き](#overwriting-an-entity-with-put) - -
- - - -# Merge-Patch と PUT (Merge-Patch and Put) - -> "Last night I dreamed about you. What happened in detail I can hardly remember, all I know is that we kept merging -> into one another. I was you, you were me. Finally you somehow caught fire" -> -> — Franz Kafka, Letters to Milena - -Merge-Patch は、リソースに対して行う一連の変更を記述するために使用される、明確に定義された -[IETF 仕様](https://www.rfc-editor.org/rfc/rfc7396.html)です。JSON ペイロードをフォレンジック・ナイフ -(a forensic knife) として使用して、エンティティ内で個別に指定された属性を作成、変更、または削除します。 -インターネット全体で定義されているように、Merge-Patch は通常 JSON ペイロードを使用し、通常は HTTP PATCH -メソッドに割り当てられるアクションです。NGSI-LD は、代わりに JSON-LD ペイロードで使用するために概念を拡張します。 - - - -## なぜ2種類の **PATCH** があるのか? (Why two kinds of **PATCH** ?) - - - -### 部分更新 **PATCH** (Partial Update **PATCH**) - -部分的な更新パッチ (Partial Update Patch) は、2 つのエンドポイント (`/entities//attrs` と -`/entities//attrs/`) でサポートされています。部分更新 **PATCH** のルールは、 -実質的に属性レベルでの上書きです。 - -次の NGSI-LD _Property_ が与えられた場合: - -```json -{ - "temperature": { - "type": "Property", - "value": 25, - "unitCode": "CEL", - "observedAt": "2022-03-14T01:59:26.535Z" - } -} -``` - -そして、次のペイロードで部分更新 **PATCH** オペレーション `/entities//attrs/temperature` を適用します。 - -```json -{ - "type": "Property", - "value": 100, - "observedAt": "2022-03-14T13:00:00.000Z" -} -``` - -#### 結果 1 - -次のように、`value` および `observedAt` サブ属性が上書きされ、`unitCode` サブ属性は変更されません。 - -```json -{ - "temperature": { - "type": "Property", - "value": 100, - "unitCode": "CEL", - "observedAt": "2022-03-14T13:00:00.000Z" - } -} -``` - -ただし、同じエンティティを指定し、`/entities//attrs` レベルで部分更新 **PATCH** 操作を適用します。 - -```json -{ - "temperature": { - "type": "Property", - "value": 100, - "observedAt": "2022-03-14T13:00:00.000Z" - } -} -``` - -#### 結果 2 - -```json -{ - "temperature": { - "type": "Property", - "value": 100, - "observedAt": "2022-03-14T13:00:00.000Z" - } -} -``` - -`temperature` プロパティ全体が上書きされます。2番目のケースでは `unitCode` も削除されていることに注意してください。 - -属性レベルでの部分更新 **PATCH** の考え方は、データの一貫性を目指すことです。`observedAt` などのサブ属性が省略された -場合、それは削除されず、既存の値が残ります。ユーザは、他の手段を使用して意図的にそのようなデータを削除することを -余儀なくされます。 - -エンティティ・レベルでの部分更新 **PATCH** の考え方は、一時的な一貫性を目指すことです。更新ごとに、最初の属性レイヤー -内のすべてのサブ属性を再供給する必要があります。`observedAt` などのサブ属性が省略されている場合、それは削除され、 -既存の一時レコードは影響を受けません。 - -**PATCH** はこれらの操作の両方に適しています。どちらの場合も、_Properties_ または _Properties of Properties_ -の選択の一部 (すべてではない) の更新であり、エンティティ自体、その `id` および `type` は変更されないためです。 - - - - -### マージ **PATCH** (Merge **PATCH**) - -マージ・パッチは `/entities/` でサポートされており、ペイロードで見つかった属性をアップサートするだけです。 -再び、次の NGSI-LD _Property_ から開始します: - -```json -{ - "temperature": { - "type": "Property", - "value": 25, - "unitCode": "CEL", - "observedAt": "2022-03-14T01:59:26.535Z" - } -} -``` - -次のペイロードでマージ **PATCH** 操作 `/entities/` を適用します。 - -```json -{ - "temperature": { - "type": "Property", - "value": 100, - "observedAt": "2022-03-14T13:00:00.000Z" - } -} -``` - -示されているように、`value` と `observedAt` サブ属性のみが更新されます: - -#### 結果 3 - -```json -{ - "temperature": { - "type": "Property", - "value": 100, - "unitCode": "CEL", - "observedAt": "2022-03-14T13:00:00.000Z" - } -} -``` - -エンティティ・レベルでのマージ **PATCH** の考え方は、一時的な一貫性を考慮せずに既存のデータを修正することです。 -変更されていないサブ属性を再供給する必要はありません。`observedAt` などのサブ属性が省略されている場合は、 -変更されたままになります。注意しないと、`observedAt` を更新せずに `value` を誤って更新する可能性があるため、 -一時的なインターフェイスで予期しない副作用が発生する可能性があります。 - -要約すると、両方のスタイルの **PATCH** 操作にそれぞれの役割がありますが、マージ **PATCH** はより焦点が絞られており、 -より小さなペイロードを使用できます。部分更新 **PATCH** は、ペイロードが完全であることを要求し、ペイロードから省略された -第 2 レベルの属性を削除することで、データの一貫性を高めます。これは `/entityOperations/upsert` エンドポイントにも -当てはまります。つまり、第 2 レベルの _Property-of-a-Property_ メタデータ属性は、削除したくない場合は常にペイロードに -含める必要があります。したがって、通常、`/entityOperations/upsert` ペイロード内のプロパティには、更新された `value` -だけでなく、`unitCode` と `observedAt` も含まれます。 - - - -### 上書き **PUT** (Overwrite **PUT**) - -HTTP **PUT** は `/entities/` でサポートされており、既存のエンティティ内のデータを上書きするだけです。この場合、 -エンティティ全体が上書きされます。以下のようなペイロードは、単一の `temperature` 属性を持つエンティティになります。 - -```json -{ - "temperature": { - "type": "Property", - "value": 25, - "unitCode": "CEL", - "observedAt": "2022-03-14T01:59:26.535Z" - } -} -``` - -**PUT** はべき等操作であることが保証されています。これを数回呼び出すと、同じシステム状態になりますが、**PATCH** -は必ずしもべき等ではなく、いずれかのフレーバー (マージ・パッチまたは部分更新パッチ) の **PATCH** ペイロードは、 -毎回エンティティ・データ全体からすべての属性を提供する必要はありません。 - - - -# アーキテクチャ - -必要なアーキテクチャは、次の3つの要素で構成されます: - -- [Orion Context Broker](https://fiware-orion.readthedocs.io/en/latest/) は、 - [NGSI-LD](https://forge.etsi.org/swagger/ui/?url=https://forge.etsi.org/rep/NGSI-LD/NGSI-LD/raw/master/spec/updated/generated/full_api.json) - を使用してリクエストを受け取ります -- 基礎となる [MongoDB](https://www.mongodb.com/) データベース: - - データ エンティティ、サブスクリプション、レジストレーションなどのコンテキスト・データ情報を保持するために - Orion Context Broker によって使用されます -- HTTP **Web-Server** は、システム内のコンテキスト・エンティティを定義する静的な `@context` ファイルを提供します - -3 つの要素間のすべての対話は HTTP リクエストによって開始されるため、要素をコンテナ化して、公開されたポートから -実行できます。 - -![](https://fiware.github.io/tutorials.CRUD-Operations/img/architecture-ld.png) - - -必要な構成情報は、関連する `docker-compose.yml` ファイルの services セクションで確認できます。 -以前のチュートリアルで説明されています。 - - - -# 前提条件 - - - -## Docker と Docker Compose - -シンプルにするために、すべてのコンポーネントは [Docker](https://www.docker.com) を使用して実行されます。**Docker** -は、それぞれの環境に分離されたさまざまなコンポーネントを可能にするコンテナ・テクノロジです。 - -- Windows に Docker をインストールするには、[こちら](https://docs.docker.com/docker-for-windows/)の指示に従ってください -- Mac に Docker をインストールするには、[こちら](https://docs.docker.com/docker-for-mac/)の指示に従ってください -- Linux に Docker をインストールするには、[こちら](https://docs.docker.com/install/)の手順に従ってください - -**Docker Compose** は、マルチコンテナ Docker アプリケーションを定義して実行するためのツールです。 -[YAMLファイル](https://raw.githubusercontent.com/FIWARE/tutorials.Merge-Patch-Put/NGSI-LD/docker-compose.yml) -を使用して、アプリケーションに必要なサービスを設定します。これは、すべてのコンテナ・サービスを単一のコマンドで起動 -できることを意味します。Docker Compose は、Docker for Windows および Docker for Mac の一部としてデフォルトでインストール -されますが、Linux ユーザは[こちら](https://docs.docker.com/compose/install/)にある手順に従う必要があります。 - -次のコマンドを使用して、現在の **Docker** および **Docker Compose** のバージョンを確認できます: - -```console -docker-compose -v -docker version -``` - -Docker バージョン 20.10 以降および Docker Compose 1.29 以降を使用していることを確認し、 -必要に応じてアップグレードしてください。 - - - -## Cygwin for Windows - -簡単な bash スクリプトを使ってサービスを開始します。Windows ユーザは、Windows 上の Linux ディストリビューションに -似たコマンドライン機能を提供するために [cygwin](http://www.cygwin.com/) をダウンロードするべきです。 - - - -# 起動 - -開始する前に、必要な Docker イメージをローカルで取得またはビルドしていることを確認する必要があります。 -次のコマンドを実行して、リポジトリのクローンを作成し、必要なイメージを作成してください: - -```console -git clone https://github.com/FIWARE/tutorials.Merge-Patch-Put.git -cd tutorials.Merge-Patch-Put -git checkout NGSI-LD - -./services create -``` - -その後、リポジトリ内で提供される [services](https://github.com/FIWARE/tutorials.Merge-Patch-Put/blob/NGSI-LD/services) -Bash スクリプトを実行することにより、コマンドラインからすべてのサービスを初期化できます: - -```console -./services start -``` - -この起動スクリプトは、2つの City エンティティも Context Broker にプリロードします。 - -> **注:** クリーンアップして最初からやり直す場合は、次のコマンドで実行できます: -> -> ```console -> ./services stop -> ``` - ---- - - - -# マージ・パッチ操作 (Merge Patch Operations) - - - -## プリフライト (Preflight) - -Orion Context Broker は **OPTIONS** メソッドをサポートし、サポートされている操作をユーザがリクエストできるように -します。2種類の **PATCH** 操作は、Accept-Patch ヘッダを読み取ることで区別できます。 - -#### :one: リクエスト: - -```console -curl -iX OPTIONS \ - 'http://localhost:1026/ngsi-ld/v1/entities/' -``` - -#### レスポンス: - -`/entities/` エンドポイントは **GET** および **POST** 操作のみをサポートします。 - -```text -HTTP/1.1 200 OK -Date: Tue, 06 Dec 2022 09:36:42 GMT -Allow: GET,POST,OPTIONS -Content-Length: 0 -``` - -#### :two: リクエスト: - -```console -curl -iX OPTIONS \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' -``` - -#### レスポンス: - -`/entities/` エンドポイントは、**GET**, **PUT**, **DELETE** および **PATCH** 操作のみをサポートします。 -**PATCH** がサポートされているため、適切なペイロード・タイプをリストする追加の `Accept-Patch` ヘッダが返されます。 -`/entities/` はマージ・パッチ・エンドポイントであるため、このリストには `application/merge-patch+json` -が含まれていることに注意してください。 - -```text -HTTP/1.1 200 OK -Date: Tue, 06 Dec 2022 09:49:43 GMT -Accept-Patch: application/json, application/ld+json, application/merge-patch+json -Allow: GET,PUT,DELETE,PATCH,OPTIONS -Content-Length: 0 -``` - -#### :three: リクエスト: - -```console -curl -iX OPTIONS \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001/attrs' -``` - -#### レスポンス: - -`/entities//attrs/temperature` エンドポイントは、**POST** および **PATCH** 操作のみをサポートします。 -`/entities//attrs` は部分更新パッチ・エンドポイントであるため、追加の `Accept-Patch` ヘッダには -`application/merge-patch+json` は含まれません。 - -```text -HTTP/1.1 200 OK -Date: Tue, 06 Dec 2022 09:49:27 GMT -Accept-Patch: application/json, application/ld+json -Allow: POST,PATCH,OPTIONS -Content-Length: 0 -``` - -#### :four: リクエスト: - -```console -curl -iX OPTIONS \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001/attrs/temperature' -``` - -#### レスポンス: - -`/entities//attrs/` エンドポイントは、**DELETE** および **PATCH** メソッドのみをサポートします。 -`/entities//attrs/` は部分更新パッチ・エンドポイントであるため、追加の `Accept-Patch` -ヘッダには `application/merge-patch+json` は含まれません。 - -```text -HTTP/1.1 200 OK -Date: Tue, 06 Dec 2022 09:49:10 GMT -Accept-Patch: application/json, application/ld+json -Allow: DELETE,PATCH,OPTIONS -Content-Length: -``` - - - -## Merge-Patch 操作 (Merge-Patch Operations) - -マージ・パッチ (Merge-Patch) による修正のために、2つの既存エンティティが作成されていることに注意してください。 -エンティティの現在の状態は、`/entities/` エンドポイントに対して **GET** リクエストを行うことで -取得できます。これらのリクエストは、各操作後にエンティティがどのように変化したかを確認するために行うことができます。 - -#### :five: リクエスト: - -```console -curl -L -X GET \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Accept: application/json' -``` - -#### レスポンス: - -```json -{ - "id": "urn:ngsi-ld:City:001", - "type": "City", - "temperature": { - "type": "Property", - "value": 25, - "unitCode": "CEL", - "observedAt": "2022-06-30T00:00:00.000Z" - }, - "location": { - "type": "GeoProperty", - "value": { - "type": "Point", - "coordinates": [28.955, 41.0136] - } - }, - "population": { - "type": "Property", - "value": 15840900, - "observedAt": "2022-12-31T00:00:00.000Z" - }, - "address": { - "type": "Property", - "value": { - "streetAddress": "Kanlıca İskele Meydanı", - "addressRegion": "İstanbul", - "addressLocality": "Beşiktaş", - "postalCode": "12345" - } - }, - "name": { - "type": "LanguageProperty", - "languageMap": { - "el": "Κωνσταντινούπολις", - "en": "Constantinople", - "tr": "İstanbul" - } - }, - "runBy": { - "type": "Relationship", - "object": "urn:ngsi-ld:Adminstration:Cumhuriyet_Halk_Partisi" - } -} -``` - -#### :six: リクエスト: - -```console -curl -L -X GET \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:002' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Accept: application/json' \ --d 'options=concise' -``` - -#### レスポンス: - -```json -{ - "id": "urn:ngsi-ld:City:002", - "type": "City", - "temperature": { - "value": 25, - "unitCode": "CEL", - "observedAt": "2022-06-30T00:00:00.000Z" - }, - "address": { - "value": { - "streetAddress": "Viale di Valle Aurelia", - "addressRegion": "Lazio", - "addressLocality": "Roma", - "postalCode": "00138" - } - }, - "location": { - "type": "Point", - "coordinates": [12.482, 41.893] - }, - "population": { - "value": 4342212, - "observedAt": "2021-01-01T00:00:00.000Z" - }, - "name": { - "languageMap": { - "el": "Ρώμη", - "en": "Rome", - "it": "Roma" - } - }, - "runBy": { - "object": "urn:ngsi-ld:Adminstration:Partito_Democratico" - } -} -``` - - - -### マージ・パッチを使用した更新 (Updating using Merge Patch) - -この例では、都市の `location` を北緯52.5146、東経13.350に移動し、`temperature` を20に修正します。 -ここのデータは正規化された形式 (normalized format) ですが、簡潔な形式 (concise format) もサポートされています: - -#### :seven::A: リクエスト: - -```console -curl -L -X PATCH \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Content-Type: application/json' \ ---data-raw '{ - "temperature": { - "type": "Property", - "value": 25 - }, - "location": { - "type": "GeoProperty", - "value": { - "type": "Point", - "coordinates": [ - 28.955, - 41.0136 - ] - } - } -}' -``` - -#### :seven::B: リクエスト: - -```console -curl -L -X PATCH \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Content-Type: application/json' \ ---data-raw '{ - "temperature": 20, - "location": { - "type": "Point", - "coordinates": [ - 13.3505, - 52.5146 - ] - } -}' -``` - -#### :eight: リクエスト: - -`urn:ngsi-ld:City:001` を再取得すると、`location` と `temperature` が変更されていることがわかりますが、他のすべての -_Properties_ と、`unitCode` や `observedAt` などの _Properties of Properties_ は変更されていません: - -```console -curl -L -X GET 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Accept: application/json' -``` - -#### レスポンス: - -```json -{ - "id": "urn:ngsi-ld:City:001", - "type": "City", - "temperature": { - "type": "Property", - "value": 20, - "unitCode": "CEL", - "observedAt": "2022-06-30T00:00:00.000Z" - }, - "location": { - "type": "GeoProperty", - "value": { - "type": "Point", - "coordinates": [13.3505, 52.5146] - } - }, - "population": { - "type": "Property", - "value": 15840900, - "observedAt": "2022-12-31T00:00:00.000Z" - }, - "address": { - "type": "Property", - "value": { - "streetAddress": "Kanlıca İskele Meydanı", - "addressRegion": "İstanbul", - "addressLocality": "Beşiktaş", - "postalCode": "12345" - } - }, - "name": { - "type": "LanguageProperty", - "languageMap": { - "el": "Κωνσταντινούπολις", - "en": "Constantinople", - "tr": "İstanbul" - } - }, - "runBy": { - "type": "Relationship", - "object": "urn:ngsi-ld:Adminstration:Cumhuriyet_Halk_Partisi" - } -} -``` - - - -### マージ・パッチを使用して新しい属性を追加 (Adding new attributes using Merge Patch) - -マージ・パッチ操作では、属性がペイロードに含まれていてもエンティティにない場合、それが挿入されます。この例では、 -`temperature` 属性が更新され、`value` と `observedAt` が更新されていますが、`precision` (精度) の -_Property of a Property_ が挿入されています。 - -いつものように、正規化された形式と簡潔な形式の両方がサポートされています。不明な属性のデフォルトは _Property_ -で、簡潔な _Relationship_ または、_LanguageProperty_ を挿入して、`object` または `languageMap` を期待どおりに含めます。 - -#### :nine::A: リクエスト: - -```console -curl -L -X PATCH \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Content-Type: application/json' \ ---data-raw '{ - "temperature": { - "type": "Property", - "value": 7, - "observedAt": "2022-03-14T12:51:02.000Z", - "precision": { - "value": 0.95, - "type": "Property", - "unitCode": "C62" - } - } -}' -``` - -#### :nine::B: リクエスト: - -```console -curl -L -X PATCH \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Content-Type: application/json' \ ---data-raw '{ - "temperature": { - "value": 7, - "observedAt": "2022-03-14T12:51:02.000Z", - "precision": { - "value": 0.95, - "unitCode": "C62" - } - } -}' -``` - -#### :one::zero: リクエスト: - -`urn:ngsi-ld:City:001` を再取得すると、`temperature` が変化し、新しい `precision` (精度) の _Property of a Property_ -が挿入されていることがわかります。 - -```console -curl -G -X GET \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Accept: application/json' \ --d 'attrs=temperature' \ -``` - -#### レスポンス: - -```json -{ - "id": "urn:ngsi-ld:City:001", - "type": "City", - "temperature": { - "type": "Property", - "value": 7, - "unitCode": "CEL", - "observedAt": "2022-03-14T12:51:02.000Z", - "precision": { - "type": "Property", - "value": 0.95, - "unitCode": "C62" - } - } -} -``` - - - -### マージ・パッチを使用して既存の属性を削除 (Removing existing attributes using Merge Patch) - -通常、マージ・パッチ操作では削除を示すために `null` が使用されます。ただし、JSON-LD はこれをサポートしていません -(`null` を持つ属性は展開時にペイロードから常に削除されるため)、代わりに NGSI-LD がプレースホルダー値 `urn:ngsi-ld:null` -を使用します。`urn:ngsi-ld:null` は、_Property_, _Relationship_, または _LanguageProperty_ の削除にも同様に有効である -ことに注意してください。以下の簡潔な例では、挿入、更新、および削除を同時に適用できます。 - -#### :one::one: リクエスト: - -```console -curl -L -X PATCH \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:002' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Content-Type: application/json' \ ---data-raw '{ - "humidity": 80, - "name": { - "languageMap": { - "el": "Βερολίνο", - "en": "Berlin", - "it": "Berlino" - } - }, - "temperature": "urn:ngsi-ld:null" -}' - -``` - -#### :one::two: リクエスト: - -`urn:ngsi-ld:City:002` を再度取得すると、`temperature` が削除され、新しい `humidity` _Property_ が挿入され、 -`name` が更新されていることがわかります。 - -```console -curl -G -X GET \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:002' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Accept: application/json' \ --d 'options=concise' -``` - -#### レスポンス: - -```json -{ - "id": "urn:ngsi-ld:City:002", - "type": "City", - "address": { - "type": "Property", - "value": { - "streetAddress": "Viale di Valle Aurelia", - "addressRegion": "Lazio", - "addressLocality": "Roma", - "postalCode": "00138" - } - }, - "location": { - "type": "GeoProperty", - "value": { - "type": "Point", - "coordinates": [12.482, 41.893] - } - }, - "population": { - "type": "Property", - "value": 4342212, - "observedAt": "2021-01-01T00:00:00.000Z" - }, - "name": { - "type": "LanguageProperty", - "languageMap": { - "el": "Βερολίνο", - "en": "Berlin", - "it": "Berlino" - } - }, - "runBy": { - "type": "Relationship", - "object": "urn:ngsi-ld:Adminstration:Partito_Democratico" - }, - "humidity": { - "type": "Property", - "value": 80 - } -} -``` - - - -### サブ属性を使用してプロパティの値を修正 (Amending values of a Property with sub-attributes) - -#### :one::three: リクエスト: - -簡潔な形式を使用すると、JSON オブジェクトの属性と _Properties of Properties_ を区別する必要があります。この場合、 -`value` の使用は、更新される `address` オブジェクトの `addressLocality` および `postalCode` であり、`verified` -_Property of a Property_ がメタデータ属性であることを示しています。 - -```console -curl -L -X PATCH \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Content-Type: application/json' \ ---data-raw '{ - "address": { - "value": { - "addressLocality": "Fenerbahçe", - "postalCode": "34567" - }, - "verified": "true" - } -}' -``` - -#### :one::four: リクエスト: - -`urn:ngsi-ld:City:001` を再度取得すると、`address` とそのプロパティ (properties) が更新されていることがわかります。 - -```console -curl -G -X GET \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Accept: application/json' \ --d 'attrs=address' \ -``` - -#### レスポンス: - -```json -{ - "id": "urn:ngsi-ld:City:001", - "type": "City", - "address": { - "type": "Property", - "value": { - "streetAddress": "Kanlıca İskele Meydanı", - "addressRegion": "İstanbul", - "addressLocality": "Fenerbahçe", - "postalCode": "34567" - }, - "verified": { - "type": "Property", - "value": "true" - } - } -} -``` - - - -### Key-Value フォーマットを使用した更新 (Updating using key-values format) - -Merge-Patch は、キー・バリュー形式を使用して `values` を更新するための限定的なサポートも提供します。この場合、 -既存の `value` は更新されますが、メタデータは変更されません。この場合も、オブジェクト値はサブ属性を送信して -更新するだけでよく、サブ属性を `urn:ngsi-ld:null` に設定すると、サブ属性が削除されます。 - -これは、キー・バリューのエンティティを **GET** (取得)し、値を **PATCH** (パッチ)して、それを Context Broker -に戻すことができることを意味します。 - -#### :one::five: リクエスト: - -```console -curl -G -X PATCH \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --d 'options=keyValues' \ --H 'Content-Type: application/json' \ ---data-raw '{ - "temperature": 19, - "location": { - "type": "Point", - "coordinates": [ - 13.3505, - 52.5146 - ] - }, - "address": { - "addressLocality": "Beyoğlu", - "postalCode": "98765" - }, - "runBy": "urn:ngsi-ld:Adminstration:Adalet_ve_Kalkınma_Partisi" -}' -``` - -#### :one::six: リクエスト: - -`urn:ngsi-ld:City:001` エンティティを再度取得すると、属性が更新されていることがわかります。_Relationship_ `runBy` -はまだ _Relationship_ として定義されていることに注意してください。変更されたのは、`object` の値だけです。 - -```console -curl -G -X GET \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Accept: application/json' \ --d 'attrs=address,temperature,location,runBy' \ -``` - -#### レスポンス: - -```json -{ - "id": "urn:ngsi-ld:City:001", - "type": "City", - "temperature": { - "type": "Property", - "value": 19, - "unitCode": "CEL", - "observedAt": "2022-06-30T00:00:00.000Z" - }, - "location": { - "type": "GeoProperty", - "value": { - "type": "Point", - "coordinates": [13.3505, 52.5146] - } - }, - "address": { - "type": "Property", - "value": { - "streetAddress": "Kanlıca İskele Meydanı", - "addressRegion": "İstanbul", - "addressLocality": "Beyoğlu", - "postalCode": "98765" - } - }, - "runBy": { - "type": "Relationship", - "object": "urn:ngsi-ld:Adminstration:Adalet_ve_Kalkınma_Partisi" - } -} -``` - - - -### `observedAt` による Key-Value を使用した更新 (Updating using key-values with `observedAt`) - -`observedAt` は Context Broker 内で一貫した一時データを維持するために非常に重要であるため、マージ・パッチ中に -キー・バリューを更新するときに追加パラメータとして提供されます。既存の _Property_ がすでに `observedAt` -の _Property of a Property_ を使用している場合、タイムスタンプも更新されます。 - -次の例では、`location` と `temperature` の両方の属性を更新します: - -#### :one::seven: リクエスト: - -```console -curl -G -X PATCH \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Content-Type: application/json' \ --d 'options=keyValues' \ --d 'observedAt=2022-10-10T10:10:00.000Z' \ ---data-raw '{ - "temperature": 19, - "location": { - "type": "Point", - "coordinates": [ - 13.3505, - 52.5146 - ] - } -}' -``` - -`urn:ngsi-ld:City:001` エンティティを再度取得すると、属性が更新されていることがわかります。今回はタイムスタンプも -変更されています。 - -#### :one::eight: リクエスト: - -```console -curl -G -X GET \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Accept: application/json' \ --d 'attrs=temperature,location' \ -``` - -#### レスポンス: - -`observedAt` は常に更新されるだけであることに注意してください。 以前に存在しなかった _Property_ には追加されません。 - -```json -{ - "id": "urn:ngsi-ld:City:001", - "type": "City", - "temperature": { - "type": "Property", - "value": 19, - "unitCode": "CEL", - "observedAt": "2022-10-10T10:10:00.000Z" - }, - "location": { - "type": "GeoProperty", - "value": { - "type": "Point", - "coordinates": [13.3505, 52.5146] - } - } -} -``` - - - -### `lang` による Key-Value を使用した更新 (Updating using key-values with `lang`) - -**GET** を使用してエンティティを取得する場合、`lang` パラメータは、属性の型を `languageMap` から単一の文字列または -文字列配列に切り替えます。これは明らかに損失の多い操作であり、キー・バリューのマージ・パッチが LanguageProperties -を持つエンティティを完全にサポートするためには、単純な文字列値を `languageMap` にマージできる必要があります。 - -#### :one::nine: リクエスト: - -```console -curl -G -X PATCH \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Content-Type: application/json' \ --d 'options=keyValues' \ --d 'lang=en' ---data-raw '{ - "temperature": 19, - "population": 15850000, - "name": "Istanbul, not Constantinople" -}' -``` - -#### :two::zero: リクエスト: - -```console -curl -G -X GET \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Accept: application/json' \ --d 'options=keyValues' \ --d 'attrs=temperature,population,name' -``` - -#### レスポンス: - -ご覧のとおり、英語 (`en`) の `name` 属性は更新されていますが、ギリシャ語 (`el`) とトルコ語 (`tr`) -の値は変更されていません。 - -```json -{ - "id": "urn:ngsi-ld:City:001", - "type": "City", - "temperature": { - "type": "Property", - "value": 19, - "unitCode": "CEL", - "observedAt": "2022-10-10T10:10:00.000Z" - }, - "population": { - "type": "Property", - "value": 15850000, - "observedAt": "2022-12-31T00:00:00.000Z" - }, - "name": { - "type": "LanguageProperty", - "languageMap": { - "el": "Κωνσταντινούπολις", - "en": "Istanbul, not Constantinople", - "tr": "İstanbul" - } - } -} -``` - - - -### **PUT** によるエンティティの上書き (Overwriting an entity with **PUT**) - -上書き操作の場合、既存の属性がペイロード・エンティティに含まれていない場合は削除されます。この例では、 -`temperature`, `population` および `name` が更新され、エンティティのその他の属性はすべて削除されます。 - -いつものように、正規化された形式と簡潔な形式の両方がサポートされています。 - -#### :two::one::A: リクエスト: - -```console -curl -G -X PUT \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:002' \ --H 'Content-Type: application/json' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ ---data-raw '{ - - "type": "City", - "temperature": { - "type": "Property", - "value": 25, - "unitCode": "CEL", - "observedAt": "2022-06-30T00:00:00.000Z" - }, - "location": { - "type": "GeoProperty", - "value": { - "type": "Point", - "coordinates": [ - 12.482, - 41.893 - ] - } - }, - "name": { - "type": "LanguageProperty", - "languageMap": { - "el": "Ρώμη", - "en": "Rome", - "it": "Roma" - } - } -}' -``` - -#### :two::one::B: リクエスト: - -```console -curl -G -X PUT \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:002' \ --H 'Content-Type: application/json' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ ---data-raw '{ - - "type": "City", - "temperature": { - "value": 25, - "unitCode": "CEL", - "observedAt": "2022-06-30T00:00:00.000Z" - }, - "location": { - "type": "Point", - "coordinates": [ - 12.482, - 41.893 - ] - }, - "name": { - "languageMap": { - "el": "Ρώμη", - "en": "Rome", - "it": "Roma" - } - } -}' -``` - -# 次のステップ - -高度な機能を追加することで、アプリケーションに複雑さを加える方法を知りたいですか? このシリーズの -[他のチュートリアル](https://www.letsfiware.jp/ngsi-ld-tutorials)を読むことで見つけることができます - ---- - -## License - -[MIT](LICENSE) © 2022 FIWARE Foundation e.V. diff --git a/README.md b/README.md index 8f2a886..4a3f36a 100644 --- a/README.md +++ b/README.md @@ -1,280 +1,21 @@ -# Merge Patch NGSI-LD[](https://www.etsi.org/deliver/etsi_gs/CIM/001_099/009/01.06.01_60/gs_CIM009v010601p.pdf)[](https://www.fiware.org/)
+[![FIWARE Banner](https://fiware.github.io/tutorials.Merge-Patch-Put/img/fiware.png)](https://www.fiware.org/developers) [![FIWARE Core Context Management](https://nexus.lab.fiware.org/repository/raw/public/badges/chapters/core.svg)](https://github.com/FIWARE/catalogue/blob/master/core/README.md) -[![License: MIT](https://img.shields.io/github/license/fiware/tutorials.Merge-Patch-Put.svg)](https://opensource.org/licenses/MIT) +[![License: MIT](https://img.shields.io/github/license/FIWARE/tutorials.Getting-Started.svg)](https://opensource.org/licenses/MIT) [![Support badge](https://img.shields.io/badge/tag-fiware-orange.svg?logo=stackoverflow)](https://stackoverflow.com/questions/tagged/fiware) -
[![JSON LD](https://img.shields.io/badge/JSON--LD-1.1-f06f38.svg)](https://w3c.github.io/json-ld-syntax/) -[![Documentation](https://img.shields.io/readthedocs/fiware-tutorials.svg)](https://fiware-tutorials.rtfd.io) +[![JSON LD](https://img.shields.io/badge/JSON--LD-1.1-f06f38.svg)](https://w3c.github.io/json-ld-syntax/) This tutorial introduces the NGSI-LD Merge Patch endpoint. It explains the difference between Merge Patch (`/entities/`) and Partial Update Patch (`/entities//attrs`) and demonstrates the use of this functionality. The tutorial uses [cUrl](https://ec.haxx.se/) commands throughout, but is also available as -[Postman documentation](https://fiware.github.io/tutorials.Merge-Patch-Put/ngsi-ld.html) +[Postman documentation](https://www.postman.com/downloads/) -[![Run in Postman](https://run.pstmn.io/button.svg)](https://app.getpostman.com/run-collection/d24facc3c430bb5d5aaf) -[![Open in Gitpod](https://gitpod.io/button/open-in-gitpod.svg)](https://gitpod.io/#https://github.com/FIWARE/tutorials.Merge-Patch-Put/tree/NGSI-LD) +# Start-Up -- このチュートリアルは[日本語](README.ja.md)でもご覧いただけます。 +## NGSI-LD Smart Farm -## Contents - -
-Details - -- [Merge-Patch and Put](#merge-patch-and-put) - - [Why two kinds of **PATCH** ?](#why-two-kinds-of-patch-) - - [Partial Update **PATCH**](#partial-update-patch) - - [Merge **PATCH**](#merge-patch) - - [Overwrite **PUT**](#overwrite-put) -- [Architecture](#architecture) -- [Prerequisites](#prerequisites) - - [Docker and Docker Compose](#docker-and-docker-compose) - - [Cygwin for Windows](#cygwin-for-windows) -- [Start Up](#start-up) -- [Merge Patch Operations](#merge-patch-operations) - - [Preflight](#preflight) - - [Merge-Patch Operations](#merge-patch-operations-1) - - [Updating using Merge Patch](#updating-using-merge-patch) - - [Adding new attributes using Merge Patch](#adding-new-attributes-using-merge-patch) - - [Removing existing attributes using Merge Patch](#removing-existing-attributes-using-merge-patch) - - [Amending values of a Property with sub-attributes](#amending-values-of-a-property-with-sub-attributes) - - [Updating using key-values format](#updating-using-key-values-format) - - [Updating using key-values with `observedAt`](#updating-using-key-values-with-observedat) - - [Updating using key-values with `lang`](#updating-using-key-values-with-lang) - - [Overwriting an entity with **PUT**](#overwriting-an-entity-with-put) - -
- -# Merge-Patch and Put - -> "Last night I dreamed about you. What happened in detail I can hardly remember, all I know is that we kept merging -> into one another. I was you, you were me. Finally you somehow caught fire" -> -> — Franz Kafka, Letters to Milena - -The Merge-Patch is a well-defined [IETF specification](https://www.rfc-editor.org/rfc/rfc7396.html) used to describe a -set of modifications to be made on a resource. It uses a JSON payload as a forensic knife to create, modify or delete -individually specified attributes within an entity. As defined across the Internet, Merge-Patch typically uses JSON -payloads, and is an action usually assigned to the HTTP **PATCH** method. NGSI-LD extends the concept for use with -JSON-LD payloads instead. - -## Why two kinds of **PATCH** ? - -### Partial Update **PATCH** - -Partial Update Patch is supported under two endpoints - `/entities//attrs` and `/entities//attrs/`. -The rules of Partial Update **PATCH** is effectively an overwrite at the attribute level. - -Given the following NGSI-LD _Property_: - -```json -{ - "temperature": { - "type": "Property", - "value": 25, - "unitCode": "CEL", - "observedAt": "2022-03-14T01:59:26.535Z" - } -} -``` - -And applying a Partial Update **PATCH** operation `/entities//attrs/temperature` with the following payload - -```json -{ - "type": "Property", - "value": 100, - "observedAt": "2022-03-14T13:00:00.000Z" -} -``` - -#### Result 1 - -Results in an overwrite of the `value`and `observedAt` sub-Attributes, leaving the `unitCode` sub-Attribute untouched as -shown: - -```json -{ - "temperature": { - "type": "Property", - "value": 100, - "unitCode": "CEL", - "observedAt": "2022-03-14T13:00:00.000Z" - } -} -``` - -However given the same entity and applying a Partial Update **PATCH** operation at the `/entities//attrs` level - -```json -{ - "temperature": { - "type": "Property", - "value": 100, - "observedAt": "2022-03-14T13:00:00.000Z" - } -} -``` - -#### Result 2 - -```json -{ - "temperature": { - "type": "Property", - "value": 100, - "observedAt": "2022-03-14T13:00:00.000Z" - } -} -``` - -Results in an overwrite of the whole `temperature` property. Note that in the second case `unitCode` has been removed as -well. - -The idea of Partial Update **PATCH** at an attribute level is to aim for data consistency. If a sub-attribute such as -`observedAt` is omitted, then it is **not** removed, and the existing value remains. A user is forced to deliberately -delete such data using other means. - -The idea of Partial Update **PATCH** at an Entity level is to aim for temporal consistency. It is necessary to resupply -all of the sub-attributes within the first attribute layer for each update. If a sub-attribute such as `observedAt` is -omitted, then it is removed and the existing temporal record is not affected. - -**PATCH** is appropriate for both of these operation since the effect in both cases is an update of some (but not all) -aspects of a selection of _Properties_ or _Properties of Properties_ , the entity itself, its `id` and `type` remain -unchanged. - -### Merge **PATCH** - -Merge Patch is supported under `/entities/` and just upserts the attributes found in a payload. Again starting from -the following NGSI-LD _Property_: - -```json -{ - "temperature": { - "type": "Property", - "value": 25, - "unitCode": "CEL", - "observedAt": "2022-03-14T01:59:26.535Z" - } -} -``` - -Applying a merge **PATCH** operation `/entities/` with the following payload - -```json -{ - "temperature": { - "type": "Property", - "value": 100, - "observedAt": "2022-03-14T13:00:00.000Z" - } -} -``` - -Results in the update of the just the `value` and `observedAt` sub-Attributes as shown - -#### Result 3 - -```json -{ - "temperature": { - "type": "Property", - "value": 100, - "unitCode": "CEL", - "observedAt": "2022-03-14T13:00:00.000Z" - } -} -``` - -The idea of Merge **PATCH** at an Entity level is to correct existing data without regard for temporal consistency It is -not necessary to resupply unchanged sub-attributes. If a sub-attribute such as `observedAt` is omitted, then it is left -changed. If not careful, this may give rise to unexpected side-effects on the temporal interface since it is possible to -inadvertently update a `value` without updating the `observedAt`. is not affected. - -In summary, both styles of **PATCH** operation have their place, but Merge **PATCH** is more focussed and is capable of -using smaller payloads. Partial Update **PATCH** forces data to be more consistent through requiring the payload to be -complete and removing second-level attributes which are omitted from the payload. This is also the case for the -`/entityOperations/upsert` endpoint meaning that second-level _Property-of-a-Property_ metadata attributes must always -be include in the payload if they do not want to be deleted. Therefore _Properties_ within `/entityOperations/upsert` -payload will usually also include `unitCode` and `observedAt` as well as an updated `value`. - -### Overwrite **PUT** - -HTTP **PUT** is supported under `/entities/` and just overwrites the data within an existing entity. In this case -whole entity is overwritten, a payload such as the one below would result in an entity with a single `temperature` -attribute. - -```json -{ - "temperature": { - "type": "Property", - "value": 25, - "unitCode": "CEL", - "observedAt": "2022-03-14T01:59:26.535Z" - } -} -``` - -**PUT** is guaranteed to be an idemponent operation. Calling it several times will result in the same system state, -whereas **PATCH** not necessarily idemponent, and a **PATCH** payload of either flavor (merge patch or partial update -patch), does not need supply every attribute from the entire entity data each time. - -# Architecture - -The required architecture will consist of three elements: - -- The [Orion Context Broker](https://fiware-orion.readthedocs.io/en/latest/) which will receive requests using - [NGSI-LD](https://forge.etsi.org/swagger/ui/?url=https://forge.etsi.org/rep/NGSI-LD/NGSI-LD/raw/master/spec/updated/generated/full_api.json) -- The underlying [MongoDB](https://www.mongodb.com/) database: - - Used by the Orion Context Broker to hold context data information such as data entities, subscriptions and - registrations -- An HTTP **Web-Server** which offers static `@context` files defining the context entities within the system. - -Since all interactions between the three elements are initiated by HTTP requests, the elements can be containerized and -run from exposed ports. - -![](https://fiware.github.io/tutorials.CRUD-Operations/img/architecture-ld.png) - -The necessary configuration information can be seen in the services section of the associated `docker-compose.yml` file. -It has been described in a previous tutorial. - -# Prerequisites - -## Docker and Docker Compose - -To keep things simple all components will be run using [Docker](https://www.docker.com). **Docker** is a container -technology which allows to different components isolated into their respective environments. - -- To install Docker on Windows follow the instructions [here](https://docs.docker.com/docker-for-windows/) -- To install Docker on Mac follow the instructions [here](https://docs.docker.com/docker-for-mac/) -- To install Docker on Linux follow the instructions [here](https://docs.docker.com/install/) - -**Docker Compose** is a tool for defining and running multi-container Docker applications. A series of -[YAML files](https://raw.githubusercontent.com/FIWARE/tutorials.Merge-Patch-Put/NGSI-LD/docker-compose.yml) are used to -configure the required services for the application. This means all container services can be brought up in a single -command. Docker Compose is installed by default as part of Docker for Windows and Docker for Mac, however Linux users -will need to follow the instructions found [here](https://docs.docker.com/compose/install/). - -You can check your current **Docker** and **Docker Compose** versions using the following commands: - -```console -docker-compose -v -docker version -``` - -Please ensure that you are using Docker version 20.10 or higher and Docker Compose 1.29 or higher and upgrade if -necessary. - -## Cygwin for Windows - -We will start up our services using a simple Bash script. Windows users should download [cygwin](http://www.cygwin.com/) -to provide a command-line functionality similar to a Linux distribution on Windows. - -# Start Up - -Before you start, you should ensure that you have obtained or built the necessary Docker images locally. Please clone -the repository and create the necessary images by running the commands as shown: +**NGSI-LD** offers JSON-LD based interoperability used for Federations and Data Spaces. To run this tutorial with **NGSI-LD**, use the `NGSI-LD` branch. ```console git clone https://github.com/FIWARE/tutorials.Merge-Patch-Put.git @@ -282,858 +23,12 @@ cd tutorials.Merge-Patch-Put git checkout NGSI-LD ./services create +./services start ``` -Thereafter, all services can be initialized from the command-line by running the -[services](https://github.com/FIWARE/tutorials.Merge-Patch-Put/blob/NGSI-LD/services) Bash script provided within the -repository: - -```console -./services [orion|scorpio|stellio] -``` - -This start-up script also preloads two City entities into the context broker. - -> :information_source: **Note:** If you want to clean up and start over again you can do so with the following command: -> -> ```console -> ./services stop -> ``` - ---- - -# Merge Patch Operations - -## Preflight - -The Orion context broker supports the **OPTIONS** method to enable users to request the supported operations. The two -types of **PATCH** operation can be distinguished by reading the `Accept-Patch` header. - -#### :one: Request: - -```console -curl -iX OPTIONS \ - 'http://localhost:1026/ngsi-ld/v1/entities/' -``` - -#### Response: - -The `/entities/` endpoint supports **GET** and **POST** operations only. - -```text -HTTP/1.1 200 OK -Date: Tue, 06 Dec 2022 09:36:42 GMT -Allow: GET,POST,OPTIONS -Content-Length: 0 -``` - -#### :two: Request: - -```console -curl -iX OPTIONS \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' -``` - -#### Response: - -The `/entities/` endpoint supports **GET**,**PUT**,**DELETE** and **PATCH** operations only. Because -**PATCH** is supported an additional `Accept-Patch` header is returned listing the appropriate payload types. It can be -noted that this list includes `application/merge-patch+json` since `/entities/` is a merge-patch endpoint - -```text -HTTP/1.1 200 OK -Date: Tue, 06 Dec 2022 09:49:43 GMT -Accept-Patch: application/json, application/ld+json, application/merge-patch+json -Allow: GET,PUT,DELETE,PATCH,OPTIONS -Content-Length: 0 -``` - -#### :three: Request: - -```console -curl -iX OPTIONS \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001/attrs' -``` - -#### Response: - -`/entities//attrs/temperature` endpoint supports **POST** and **PATCH** operations only. The additional -`Accept-Patch` header does not include `application/merge-patch+json` since `/entities//attrs` is a partial -update patch endpoint - -```text -HTTP/1.1 200 OK -Date: Tue, 06 Dec 2022 09:49:27 GMT -Accept-Patch: application/json, application/ld+json -Allow: POST,PATCH,OPTIONS -Content-Length: 0 -``` - -#### :four: Request: - -```console -curl -iX OPTIONS \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001/attrs/temperature' -``` - -#### Response: - -`/entities//attrs/` endpoint supports **DELETE** and **PATCH** methods only. The additional -`Accept-Patch` header does not include `application/merge-patch+json` since `/entities//attrs/` is -a partial update patch endpoint - -```text -HTTP/1.1 200 OK -Date: Tue, 06 Dec 2022 09:49:10 GMT -Accept-Patch: application/json, application/ld+json -Allow: DELETE,PATCH,OPTIONS -Content-Length: -``` - -## Merge-Patch Operations - -Note that two preexisting entities have been created for amendment by Merge-Patch, the current state of the entities can -be obtained by making a **GET** request to the `/entities/` endpoint. These requests can be made to see how -the entities have changed after each operation. - -#### :five: Request: - -```console -curl -L -X GET \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Accept: application/json' -``` - -#### Response: - -```json -{ - "id": "urn:ngsi-ld:City:001", - "type": "City", - "temperature": { - "type": "Property", - "value": 25, - "unitCode": "CEL", - "observedAt": "2022-06-30T00:00:00.000Z" - }, - "location": { - "type": "GeoProperty", - "value": { - "type": "Point", - "coordinates": [28.955, 41.0136] - } - }, - "population": { - "type": "Property", - "value": 15840900, - "observedAt": "2022-12-31T00:00:00.000Z" - }, - "address": { - "type": "Property", - "value": { - "streetAddress": "Kanlıca İskele Meydanı", - "addressRegion": "İstanbul", - "addressLocality": "Beşiktaş", - "postalCode": "12345" - } - }, - "name": { - "type": "LanguageProperty", - "languageMap": { - "el": "Κωνσταντινούπολις", - "en": "Constantinople", - "tr": "İstanbul" - } - }, - "runBy": { - "type": "Relationship", - "object": "urn:ngsi-ld:Adminstration:Cumhuriyet_Halk_Partisi" - } -} -``` - -#### :six: Request: - -```console -curl -L -X GET \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:002' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Accept: application/json' \ --d 'options=concise' -``` - -#### Response: - -```json -{ - "id": "urn:ngsi-ld:City:002", - "type": "City", - "temperature": { - "value": 25, - "unitCode": "CEL", - "observedAt": "2022-06-30T00:00:00.000Z" - }, - "address": { - "value": { - "streetAddress": "Viale di Valle Aurelia", - "addressRegion": "Lazio", - "addressLocality": "Roma", - "postalCode": "00138" - } - }, - "location": { - "type": "Point", - "coordinates": [12.482, 41.893] - }, - "population": { - "value": 4342212, - "observedAt": "2021-01-01T00:00:00.000Z" - }, - "name": { - "languageMap": { - "el": "Ρώμη", - "en": "Rome", - "it": "Roma" - } - }, - "runBy": { - "object": "urn:ngsi-ld:Adminstration:Partito_Democratico" - } -} -``` - -### Updating using Merge Patch - -This example moves the city `location` to 52.5146 N,13.350 E and amends the `temperature` to 20. The data here is in -normalized format, but concise format is also supported: - -#### :seven::A: Request: - -```console -curl -L -X PATCH \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Content-Type: application/json' \ ---data-raw '{ - "temperature": { - "type": "Property", - "value": 25 - }, - "location": { - "type": "GeoProperty", - "value": { - "type": "Point", - "coordinates": [ - 28.955, - 41.0136 - ] - } - } -}' -``` - -#### :seven::B: Request: - -```console -curl -L -X PATCH \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Content-Type: application/json' \ ---data-raw '{ - "temperature": 20, - "location": { - "type": "Point", - "coordinates": [ - 13.3505, - 52.5146 - ] - } -}' -``` - -#### :eight: Request: - -Re-retrieving the `urn:ngsi-ld:City:001`, you can see that the `location` and `temperature` have changed, but all other -_Properties_ and _Properties of Properties_ such as `unitCode` and `observedAt` remain unchanged: - -```console -curl -L -X GET 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Accept: application/json' -``` - -#### Response: - -```json -{ - "id": "urn:ngsi-ld:City:001", - "type": "City", - "temperature": { - "type": "Property", - "value": 20, - "unitCode": "CEL", - "observedAt": "2022-06-30T00:00:00.000Z" - }, - "location": { - "type": "GeoProperty", - "value": { - "type": "Point", - "coordinates": [13.3505, 52.5146] - } - }, - "population": { - "type": "Property", - "value": 15840900, - "observedAt": "2022-12-31T00:00:00.000Z" - }, - "address": { - "type": "Property", - "value": { - "streetAddress": "Kanlıca İskele Meydanı", - "addressRegion": "İstanbul", - "addressLocality": "Beşiktaş", - "postalCode": "12345" - } - }, - "name": { - "type": "LanguageProperty", - "languageMap": { - "el": "Κωνσταντινούπολις", - "en": "Constantinople", - "tr": "İstanbul" - } - }, - "runBy": { - "type": "Relationship", - "object": "urn:ngsi-ld:Adminstration:Cumhuriyet_Halk_Partisi" - } -} -``` - -### Adding new attributes using Merge Patch - -For a merge patch operation, if an attribute is included in the payload but missing on the entity, it is inserted. In -this example, the `temperature` attribute is being updated, the `value` and `observedAt` have been updated, but the -`precision` _Property of a Property_ is being inserted. - -As usual, both normalized and concise formats are supported.The default for unknown attributes is _Property_, to insert -a concise _Relationship_ or a _LanguageProperty_ include `object` or `languageMap` as expected. - -#### :nine::A: Request: - -```console -curl -L -X PATCH \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Content-Type: application/json' \ ---data-raw '{ - "temperature": { - "type": "Property", - "value": 7, - "observedAt": "2022-03-14T12:51:02.000Z", - "precision": { - "value": 0.95, - "type": "Property", - "unitCode": "C62" - } - } -}' -``` - -#### :nine::B: Request: - -```console -curl -L -X PATCH \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Content-Type: application/json' \ ---data-raw '{ - "temperature": { - "value": 7, - "observedAt": "2022-03-14T12:51:02.000Z", - "precision": { - "value": 0.95, - "unitCode": "C62" - } - } -}' -``` - -#### :one::zero: Request: - -Re-retrieving the `urn:ngsi-ld:City:001`, you can see that the `temperature` have changed, and the new `precision` -_Property of a Property_ has been inserted. - -```console -curl -G -X GET \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Accept: application/json' \ --d 'attrs=temperature' \ -``` - -#### Response: - -```json -{ - "id": "urn:ngsi-ld:City:001", - "type": "City", - "temperature": { - "type": "Property", - "value": 7, - "unitCode": "CEL", - "observedAt": "2022-03-14T12:51:02.000Z", - "precision": { - "type": "Property", - "value": 0.95, - "unitCode": "C62" - } - } -} -``` - -### Removing existing attributes using Merge Patch - -Usually `null` is used in merge patch operations to indicate deletion. However, JSON-LD does not support this (since an -attribute with a `null` is always removed from the payload on expansion) and therefore NGSI-LD uses a placeholder value -`urn:ngsi-ld:null` instead. Note that `urn:ngsi-ld:null` is equally valid for deletion of a _Property_, _Relationship_ -or a _LanguageProperty_. In the concise example below, an insertion, an update and a deletion can be applied -simultaneously. - -#### :one::one: Request: - -```console -curl -L -X PATCH \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:002' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Content-Type: application/json' \ ---data-raw '{ - "humidity": 80, - "name": { - "languageMap": { - "el": "Βερολίνο", - "en": "Berlin", - "it": "Berlino" - } - }, - "temperature": "urn:ngsi-ld:null" -}' - -``` - -#### :one::two: Request: - -Re-retrieving the `urn:ngsi-ld:City:002`, you can see that the `temperature` has been removed and the new `humidity` -_Property_ has been inserted and the `name` updated. - -```console -curl -G -X GET \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:002' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Accept: application/json' \ --d 'options=concise' -``` - -#### Response: - -```json -{ - "id": "urn:ngsi-ld:City:002", - "type": "City", - "address": { - "type": "Property", - "value": { - "streetAddress": "Viale di Valle Aurelia", - "addressRegion": "Lazio", - "addressLocality": "Roma", - "postalCode": "00138" - } - }, - "location": { - "type": "GeoProperty", - "value": { - "type": "Point", - "coordinates": [12.482, 41.893] - } - }, - "population": { - "type": "Property", - "value": 4342212, - "observedAt": "2021-01-01T00:00:00.000Z" - }, - "name": { - "type": "LanguageProperty", - "languageMap": { - "el": "Βερολίνο", - "en": "Berlin", - "it": "Berlino" - } - }, - "runBy": { - "type": "Relationship", - "object": "urn:ngsi-ld:Adminstration:Partito_Democratico" - }, - "humidity": { - "type": "Property", - "value": 80 - } -} -``` - -### Amending values of a Property with sub-attributes - -#### :one::three: Request: - -Using concise format, it is necessary to distinguish between atttibutes of a JSON object and _Properties of Properties_. -In this case the use of `value` shows it is the `addressLocality` and `postalCode` of the `address` Object which is to -be updated and that `verified` the _Property of a Property_ is a metadata attribute. - -```console -curl -L -X PATCH \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Content-Type: application/json' \ ---data-raw '{ - "address": { - "value": { - "addressLocality": "Fenerbahçe", - "postalCode": "34567" - }, - "verified": "true" - } -}' -``` - -#### :one::four: Request: - -Once again retrieving the `urn:ngsi-ld:City:001`, you can see that the `address` and its properties have been updated. - -```console -curl -G -X GET \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Accept: application/json' \ --d 'attrs=address' \ -``` - -#### Response: - -```json -{ - "id": "urn:ngsi-ld:City:001", - "type": "City", - "address": { - "type": "Property", - "value": { - "streetAddress": "Kanlıca İskele Meydanı", - "addressRegion": "İstanbul", - "addressLocality": "Fenerbahçe", - "postalCode": "34567" - }, - "verified": { - "type": "Property", - "value": "true" - } - } -} -``` - -### Updating using key-values format - -Merge-Patch also offers some limited support to update `values` using key-values format. In this case any existing -`value` is updated, but no metadata is changed. Once again Object values need only send the sub-attributes to be -updated, and setting a sub-attribute to `urn:ngsi-ld:null` will cause it to be deleted. - -This means that it is possible to **GET** a key-values entity, amend the values and **PATCH** it back to the context -broker. - -#### :one::five: Request: - -```console -curl -G -X PATCH \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --d 'options=keyValues' \ --H 'Content-Type: application/json' \ ---data-raw '{ - "temperature": 19, - "location": { - "type": "Point", - "coordinates": [ - 13.3505, - 52.5146 - ] - }, - "address": { - "addressLocality": "Beyoğlu", - "postalCode": "98765" - }, - "runBy": "urn:ngsi-ld:Adminstration:Adalet_ve_Kalkınma_Partisi" -}' -``` - -#### :one::six: Request: - -Once again retrieving the `urn:ngsi-ld:City:001` entity, you can see that the attributes have been updated. It should be -noted that the _Relationship_ `runBy` is still defined as a _Relationship_, it is only the `object` value that has been -changed. - -```console -curl -G -X GET \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Accept: application/json' \ --d 'attrs=address,temperature,location,runBy' \ -``` - -#### Response: - -```json -{ - "id": "urn:ngsi-ld:City:001", - "type": "City", - "temperature": { - "type": "Property", - "value": 19, - "unitCode": "CEL", - "observedAt": "2022-06-30T00:00:00.000Z" - }, - "location": { - "type": "GeoProperty", - "value": { - "type": "Point", - "coordinates": [13.3505, 52.5146] - } - }, - "address": { - "type": "Property", - "value": { - "streetAddress": "Kanlıca İskele Meydanı", - "addressRegion": "İstanbul", - "addressLocality": "Beyoğlu", - "postalCode": "98765" - } - }, - "runBy": { - "type": "Relationship", - "object": "urn:ngsi-ld:Adminstration:Adalet_ve_Kalkınma_Partisi" - } -} -``` - -### Updating using key-values with `observedAt` - -Since `observedAt` is exceedingly important for maintaining consistent temporal data within the context broker it is -offered as an additional parameter when updating key-values during merge-patch. If a pre-existing _Property_ already -uses `observedAt` _Property of a Property of a Property_, the timestamp will also be updated. - -The following example updates both the location and temperature attributes - -#### :one::seven: Request: - -```console -curl -G -X PATCH \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Content-Type: application/json' \ --d 'options=keyValues' \ --d 'observedAt=2022-10-10T10:10:00.000Z' \ ---data-raw '{ - "temperature": 19, - "location": { - "type": "Point", - "coordinates": [ - 13.3505, - 52.5146 - ] - } -}' -``` - -Once again retrieving the `urn:ngsi-ld:City:001` entity, you can see that the attributes have been updated, and this -time the timestamp has also changed. - -#### :one::eight: Request: - -```console -curl -G -X GET \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Accept: application/json' \ --d 'attrs=temperature,location' \ -``` - -#### Response: - -Note that `observedAt` is only ever updated. It is not added to a _Property_ where it was not present previously. - -```json -{ - "id": "urn:ngsi-ld:City:001", - "type": "City", - "temperature": { - "type": "Property", - "value": 19, - "unitCode": "CEL", - "observedAt": "2022-10-10T10:10:00.000Z" - }, - "location": { - "type": "GeoProperty", - "value": { - "type": "Point", - "coordinates": [13.3505, 52.5146] - } - } -} -``` - -### Updating using key-values with `lang` - -When retrieving an entity using **GET**, the `lang` parameter switches the attribute type from a `languageMap` to a -single string or string array. This is obviously a lossy operation, and in order for key-values merge patch fully -support entities with LanguageProperties, it is necessary to be able to merge a simple string value back into a -`languageMap`. - -#### :one::nine: Request: - -```console -curl -G -X PATCH \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Content-Type: application/json' \ --d 'options=keyValues' \ --d 'lang=en' ---data-raw '{ - "temperature": 19, - "population": 15850000, - "name": "Istanbul, not Constantinople" -}' -``` - -#### :two::zero: Request: - -```console -curl -G -X GET \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:001' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Accept: application/json' \ --d 'options=keyValues' \ --d 'attrs=temperature,population,name' -``` - -#### Response: - -As can be seen, `name` attribute in English (`en`) has been updated, whereas the values in Greek (`el`) and Turkish -(`tr`) have been left untouched. - -```json -{ - "id": "urn:ngsi-ld:City:001", - "type": "City", - "temperature": { - "type": "Property", - "value": 19, - "unitCode": "CEL", - "observedAt": "2022-10-10T10:10:00.000Z" - }, - "population": { - "type": "Property", - "value": 15850000, - "observedAt": "2022-12-31T00:00:00.000Z" - }, - "name": { - "type": "LanguageProperty", - "languageMap": { - "el": "Κωνσταντινούπολις", - "en": "Istanbul, not Constantinople", - "tr": "İstanbul" - } - } -} -``` - -### Overwriting an entity with **PUT** - -For an overwrite operation, if an existing attribute is not included in the payload entity, it is deleted. In this -example, the `temperature`, `population` and `name` are being updated, any other attributes on the entity will be -deleted. - -As usual, both normalized and concise formats are supported. - -#### :two::one::A: Request: - -```console -curl -G -X PUT \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:002' \ --H 'Content-Type: application/json' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ ---data-raw '{ - - "type": "City", - "temperature": { - "type": "Property", - "value": 25, - "unitCode": "CEL", - "observedAt": "2022-06-30T00:00:00.000Z" - }, - "location": { - "type": "GeoProperty", - "value": { - "type": "Point", - "coordinates": [ - 12.482, - 41.893 - ] - } - }, - "name": { - "type": "LanguageProperty", - "languageMap": { - "el": "Ρώμη", - "en": "Rome", - "it": "Roma" - } - } -}' -``` - -#### :two::one::B: Request: - -```console -curl -G -X PUT \ - 'http://localhost:1026/ngsi-ld/v1/entities/urn:ngsi-ld:City:002' \ --H 'Content-Type: application/json' \ --H 'Link: ; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ ---data-raw '{ - - "type": "City", - "temperature": { - "value": 25, - "unitCode": "CEL", - "observedAt": "2022-06-30T00:00:00.000Z" - }, - "location": { - "type": "Point", - "coordinates": [ - 12.482, - 41.893 - ] - }, - "name": { - "languageMap": { - "el": "Ρώμη", - "en": "Rome", - "it": "Roma" - } - } -}' -``` - -# Next Steps +| [![NGSI LD](https://img.shields.io/badge/NGSI-LD-d6604d.svg)](https://www.etsi.org/deliver/etsi_gs/CIM/001_099/009/01.08.01_60/gs_cim009v010801p.pdf) | :books: [Documentation](https://github.com/FIWARE/tutorials.Merge-Patch-Put/tree/NGSI-LD) | [Postman Collection](https://fiware.github.io/tutorials.Merge-Patch-Put/ngsi-ld.html) | +| --- | --- | --- | -Want to learn how to add more complexity to your application by adding advanced features? You can find out by reading -the other [tutorials in this series](https://ngsi-ld-tutorials.rtfd.io) --- diff --git a/data-models/alternate-context.jsonld b/data-models/alternate-context.jsonld deleted file mode 100644 index c5c89cf..0000000 --- a/data-models/alternate-context.jsonld +++ /dev/null @@ -1,283 +0,0 @@ -{ - "@context": { - "type": "@type", - "id": "@id", - "ngsi-ld": "https://uri.etsi.org/ngsi-ld/", - "fiware": "https://uri.fiware.org/ns/dataModels#", - "schema": "https://schema.org/", - "rdfs": "http://www.w3.org/2000/01/rdf-schema#", - "xsd": "http://www.w3.org/2001/XMLSchema#", - "tutorial": "https://ngsi-ld-tutorials.readthedocs.io/en/latest/datamodels.html#", - "Gebäude": "fiware:Building", - "Tier": "fiware:Animal", - "Weiblich": "schema:Female", - "Gerät": "fiware:Device", - "Füllstandssensor": "tutorial:FillingLevelSensor", - "Herbicide": "tutorial:Herbicide", - "HVAC": "https://w3id.org/saref#HVAC", - "Männlich": "schema:Male", - "PartField": "tutorial:PartField", - "Person": "fiware:Person", - "SoilSensor": "tutorial:SoilSensor", - "TemperatureSensor": "fiware:TemperatureSensor", - "Activität": "fiware:Activity", - "Traktor": "tutorial:Tractor", - "Wasser": "tutorial:Water", - "aktuator": "https://w3id.org/saref#actuator", - "zusätzlicherName": "schema:additionalName", - "adresse": "schema:address", - "airPollution": "https://w3id.org/saref#airPollution", - "atmosphericPressure": "https://w3id.org/saref#atmosphericPressure", - "scheune": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dbarn", - "akku": "fiware:batteryLevel", - "kategorie": "fiware:category", - "aufbau": "fiware:configuration", - "wintergarten": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dconservatory", - "anOrtEnthalten": "fiware:containedInPlace", - "kontrollierterVermögenswert": "fiware:controlledAsset", - "kontrolliertesAttribut": "fiware:controlledProperty", - "kuhstall": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dcowshed", - "datenanbieter": "fiware:dataProvider", - "dateCreated": "fiware:dateCreated", - "dateFirstUsed": "fiware:dateFirstUsed", - "dateInstalled": "fiware:dateInstalled", - "dateLastCalibration": "fiware:dateLastCalibration", - "dateLastValueReported": "fiware:dateLastValueReported", - "dateManufactured": "fiware:dateManufactured", - "dateModified": "fiware:dateModified", - "tiefe": "https://w3id.org/saref#depth", - "beschreibung": "ngsi-ld:description", - "gerätestatus": "fiware:deviceState", - "fermenter": "https://wiki.openstreetmap.org/wiki/Tag:building%3Ddigester", - "essaktivität": "https://w3id.org/saref#eatingActivity", - "email": "schema:email", - "endgun": "https://w3id.org/saref#endgun", - "familienname": "schema:familyName", - "bauernhof": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dfarm", - "bauernhofhilfsmittel": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dfarm_auxiliary", - "faxnummer": "schema:faxNumber", - "füllstands": "https://w3id.org/saref#fillingLevel", - "firmwareVersion": "fiware:firmwareVersion", - "floorsAboveGround": "fiware:floorsAboveGround", - "floorsBelowGround": "fiware:floorsBelowGround", - "geschlecht": "schema:gender", - "vorname": "schema:givenName", - "gewächshaus": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dgreenhouse", - "hangar": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dhangar", - "hardwareVersion": "fiware:hardwareVersion", - "honorificPrefix": "schema:honorificPrefix", - "honorificSuffix": "schema:honorificSuffix", - "luftfeuchtigkeit": "https://w3id.org/saref#humidity", - "hütte": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dhut", - "werkzeug": "https://w3id.org/saref#implement", - "ipAddress": "fiware:ipAddress", - "irrSection": "https://w3id.org/saref#irrSection", - "irrSystem": "https://w3id.org/saref#irrSystem", - "isicV4": "schema:isicV4", - "berufsbezeichnung": "schema:jobTitle", - "ort": "https://w3id.org/saref#location", - "macAddress": "fiware:macAddress", - "mcc": "fiware:mcc", - "meter": "https://w3id.org/saref#meter", - "melken": "https://w3id.org/saref#milking", - "mnc": "fiware:mnc", - "bewegung": "https://w3id.org/saref#motion", - "bewegungsaktivität": "https://w3id.org/saref#movementActivity", - "multimedia": "https://w3id.org/saref#multimedia", - "name": "schema:name", - "netzwerk": "https://w3id.org/saref#network", - "belegung": "https://w3id.org/saref#occupancy", - "besatzer": "fiware:occupier", - "öffnungszeiten": "fiware:openingHours", - "osVersion": "fiware:osVersion", - "inhaber": "fiware:owner", - - "niederschlag": "https://w3id.org/saref#precipitation", - "druck": "https://w3id.org/saref#pressure", - "anbieter": "fiware:provider", - "refGeräteModell": "fiware:refDeviceModel", - - "refKarte": "fiware:refMap", - "rssi": "fiware:rssi", - "sensor": "https://w3id.org/saref#sensor", - "ordnungsnummer": "fiware:serialNumber", - "service": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dservice", - "schuppen": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dshed", - "softwareVersion": "fiware:softwareVersion", - "bodenfeuchtigkeit": "https://w3id.org/saref#soilMoisture", - "sonnenstrahlung": "https://w3id.org/saref#solarRadiation", - "quelle": "fiware:source", - "stall": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dstable", - "schweinestall": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dsty", - "supportedProtocol": "fiware:supportedProtocol", - "steuerID": "schema:taxID", - "telefon": "schema:telephone", - "temperature": "https://w3id.org/saref#temperature", - "transformator_turm": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dtransformer_tower", - "value": "fiware:value", - "vatID": "schema:vatID", - "wasserVerbrauch": "https://w3id.org/saref#waterConsumption", - "wasserturm": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dwater_tower", - "wetterbedingungen": "https://w3id.org/saref#weatherConditions", - "gewicht": "https://w3id.org/saref#weight", - "windrichtung": "https://w3id.org/saref#windDirection", - "windgeschwindigkeit": "https://w3id.org/saref#windSpeed", - - "zustand": "https://saref.etsi.org/core/hasState", - "status": "https://saref.etsi.org/core/status", - "herzschlagfrequenz": "https://purl.bioontology.org/ontology/MESH/D006339", - "produkt": "fiware:refObject", - "abeiter": "fiware:refAgent", - "feld": "fiware:refTarget", - - "ein": "https://w3id.org/saref#on", - "aus": "https://w3id.org/saref#off", - - "spezies": "fiware:species", - "sex": "fiware:sex", - "rechtlicheIdentität": "fiware:legalID", - "City": "fiware:Grossstadt" - }, - "@graph": [ - { - "@id": "fiware:Building", - "@type": "rdfs:Class", - "rdfs:comment": [ - { - "@language": "en", - "@value": "" - } - ], - "rdfs:label": [ - { - "@language": "en", - "@value": "Building" - } - ], - "rdfs:subClassOf": { - "@id": "schema:Thing" - } - }, - { - "@id": "fiware:TemperatureSensor", - "@type": "rdfs:Class", - "rdfs:comment": [ - { - "@language": "en", - "@value": "A device that consists of a sensor, has category `saref:Sensor` and is used for the purpose of sensing temperature`." - } - ], - "rdfs:label": [ - { - "@language": "en", - "@value": "TemperatureSensor" - } - ], - "rdfs:subClassOf": { - "@id": "schema:Thing" - } - }, - { - "@id": "fiware:FillingLevelSensor", - "@type": "rdfs:Class", - "rdfs:comment": [ - { - "@language": "en", - "@value": "A device that consists of a sensor, has category `saref:Sensor` and is used for the purpose of sensing filling Level." - } - ], - "rdfs:label": [ - { - "@language": "en", - "@value": "FillingLevelSensor" - } - ], - "rdfs:subClassOf": { - "@id": "schema:Thing" - } - }, - { - "@id": "fiware:Person", - "@type": "rdfs:Class", - "rdfs:comment": [ - { - "@language": "en", - "@value": "" - } - ], - "rdfs:label": [ - { - "@language": "en", - "@value": "Person" - } - ], - "rdfs:subClassOf": { - "@id": "schema:Thing" - } - }, - { - "@id": "fiware:temperature", - "@type": "ngsi-ld:Property", - "rdfs:comment": [ - { - "@language": "en", - "@value": "Property related to some measurements that are characterized by a certain value that is measured in a temperature unit (degree_Celsius, degree_Fahrenheit, or degree_kelvin)" - } - ], - "rdfs:label": [ - { - "@language": "en", - "@value": "temperature" - } - ] - }, - { - "@id": "fiware:fillingLevel", - "@type": "ngsi-ld:Property", - "rdfs:comment": [ - { - "@language": "en", - "@value": "Property related to some measurements that are characterized by a certain value that is a filling level." - } - ], - "rdfs:label": [ - { - "@language": "en", - "@value": "fillingLevel" - } - ] - }, - { - "@id": "fiware:temperature", - "@type": "ngsi-ld:Property", - "rdfs:comment": [ - { - "@language": "en", - "@value": "Property related to some measurements that are characterized by a certain value that is measured in a temperature unit (degree_Celsius, degree_Fahrenheit, or degree_kelvin)" - } - ], - "rdfs:label": [ - { - "@language": "en", - "@value": "temperature" - } - ] - }, - { - "@id": "fiware:fillingLevel", - "@type": "ngsi-ld:Property", - "rdfs:comment": [ - { - "@language": "en", - "@value": "Property related to some measurements that are characterized by a certain value that is a filling level." - } - ], - "rdfs:label": [ - { - "@language": "en", - "@value": "fillingLevel" - } - ] - } - ] -} diff --git a/data-models/anomaly.jsonld b/data-models/anomaly.jsonld deleted file mode 100644 index f2eff9e..0000000 --- a/data-models/anomaly.jsonld +++ /dev/null @@ -1,35 +0,0 @@ -{ - "@context": { - - "ngsi-ld": "https://uri.etsi.org/ngsi-ld/", - "fiware": "https://uri.fiware.org/ns/dataModels#", - "schema": "https://schema.org/", - "Anomaly": "fiware:Anomaly", - "address": "https://smartdatamodels.org/address", - "alertSource": "https://smartdatamodels.org/dataModel.Alert/alertSource", - "alternateName": "https://smartdatamodels.org/alternateName", - "anomalousProperty": "https://smartdatamodels.org/dataModel.Alert/anomalousProperty", - "areaServed": "https://smartdatamodels.org/areaServed", - "category": "https://smartdatamodels.org/dataModel.Alert/category", - "data": "ngsi-ld:data", - "dataProvider": "https://smartdatamodels.org/dataProvider", - "dateCreated": "https://smartdatamodels.org/dateCreated", - "dateDetected": "https://smartdatamodels.org/dataModel.Alert/dateDetected", - "dateIssued": "https://smartdatamodels.org/dataModel.Alert/dateIssued", - "dateModified": "https://smartdatamodels.org/dateModified", - "description": "http://purl.org/dc/terms/description", - "detectedBy": "https://smartdatamodels.org/dataModel.Alert/detectedBy", - "id": "@id", - "location": "ngsi-ld:location", - "name": "https://smartdatamodels.org/name", - "owner": "https://smartdatamodels.org/owner", - "seeAlso": "https://smartdatamodels.org/seeAlso", - "severity": "https://smartdatamodels.org/dataModel.Alert/severity", - "source": "https://smartdatamodels.org/source", - "subCategory": "https://smartdatamodels.org/dataModel.Alert/subCategory", - "thresholdBreach": "https://smartdatamodels.org/dataModel.Alert/thresholdBreach", - "type": "@type", - "validFrom": "https://smartdatamodels.org/dataModel.Alert/validFrom", - "validTo": "https://smartdatamodels.org/dataModel.Alert/validTo" - } -} \ No newline at end of file diff --git a/data-models/json-context.jsonld b/data-models/json-context.jsonld deleted file mode 100644 index 0782fcb..0000000 --- a/data-models/json-context.jsonld +++ /dev/null @@ -1,441 +0,0 @@ -{ - "@context": { - "type": "@type", - "id": "@id", - "ngsi-ld": "https://uri.etsi.org/ngsi-ld/", - "fiware": "https://uri.fiware.org/ns/dataModels#", - "schema": "https://schema.org/", - "rdfs": "http://www.w3.org/2000/01/rdf-schema#", - "xsd": "http://www.w3.org/2001/XMLSchema#", - "tutorial": "https://ngsi-ld-tutorials.readthedocs.io/en/latest/datamodels.html#", - "Building": "fiware:Building", - "Device": "fiware:Device", - "Animal": "fiware:Animal", - "Female": "schema:Female", - "FillingLevelSensor": "tutorial:FillingLevelSensor", - "Herbicide": "tutorial:Product", - "HVAC": "https://w3id.org/saref#HVAC", - "Male": "schema:Male", - "PartField": "tutorial:PartField", - "Person": "fiware:Person", - "SoilSensor": "tutorial:SoilSensor", - "TemperatureSensor": "tutorial:TemperatureSensor", - "Task": "fiware:Activity", - "Tractor": "tutorial:Tractor", - "Water": "tutorial:Water", - "actuator": "https://w3id.org/saref#actuator", - "additionalName": { - "@id": "schema:additionalName", - "@type": "xsd:string" - }, - "address": "schema:address", - "airPollution": "https://w3id.org/saref#airPollution", - "atmosphericPressure": "https://w3id.org/saref#atmosphericPressure", - "barn": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dbarn", - "batteryLevel": { - "@id": "fiware:batteryLevel", - "@type": "xsd:number" - }, - "category": { - "@id": "fiware:category", - "@type": "@vocab" - }, - "configuration": { - "@id": "fiware:configuration", - "@type": "xsd:string" - }, - "conservatory": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dconservatory", - "containedInPlace": { - "@id": "fiware:containedInPlace", - "@type": "@id" - }, - "controlledAsset": { - "@id": "fiware:controlledAsset", - "@type": "@id" - }, - "controlledProperty": { - "@id": "fiware:controlledProperty", - "@type": "@vocab" - }, - "cowshed": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dcowshed", - "dataProvider": { - "@id": "fiware:dataProvider", - "@type": "xsd:string" - }, - "dateCreated": { - "@id": "fiware:dateCreated", - "@type": "xs:dateTime" - }, - "dateFirstUsed": { - "@id": "fiware:dateFirstUsed", - "@type": "xs:dateTime" - }, - "dateInstalled": { - "@id": "fiware:dateInstalled", - "@type": "xs:dateTime" - }, - "dateLastCalibration": { - "@id": "fiware:dateLastCalibration", - "@type": "xs:dateTime" - }, - "dateLastValueReported": { - "@id": "fiware:dateLastValueReported", - "@type": "xs:dateTime" - }, - "dateManufactured": { - "@id": "fiware:dateManufactured", - "@type": "xs:dateTime" - }, - "dateModified": { - "@id": "fiware:dateModified", - "@type": "xs:dateTime" - }, - "depth": "https://w3id.org/saref#depth", - "description": { - "@id": "ngsi-ld:description", - "@type": "xsd:string" - }, - "deviceState": { - "@id": "fiware:deviceState", - "@type": "xsd:string" - }, - "digester": "https://wiki.openstreetmap.org/wiki/Tag:building%3Ddigester", - "eatingActivity": "https://w3id.org/saref#eatingActivity", - "email": { - "@id": "schema:email", - "@type": "xsd:string" - }, - "endgun": "https://w3id.org/saref#endgun", - "familyName": { - "@id": "schema:familyName", - "@type": "xsd:string" - }, - "farm": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dfarm", - "farm_auxiliary": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dfarm_auxiliary", - "faxNumber": { - "@id": "schema:faxNumber", - "@type": "xsd:string" - }, - "filling": "https://w3id.org/saref#fillingLevel", - "firmwareVersion": { - "@id": "fiware:firmwareVersion", - "@type": "xsd:string" - }, - "floorsAboveGround": { - "@id": "fiware:floorsAboveGround", - "@type": "xsd:integer" - }, - "floorsBelowGround": { - "@id": "fiware:floorsBelowGround", - "@type": "xsd:integer" - }, - "gender": { - "@id": "schema:gender", - "@type": "@vocab" - }, - "givenName": { - "@id": "schema:givenName", - "@type": "xsd:string" - }, - "greenhouse": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dgreenhouse", - "hangar": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dhangar", - "hardwareVersion": { - "@id": "fiware:hardwareVersion", - "@type": "xsd:string" - }, - "honorificPrefix": { - "@id": "schema:honorificPrefix", - "@type": "xsd:string" - }, - "honorificSuffix": { - "@id": "schema:honorificSuffix", - "@type": "xsd:string" - }, - "humidity": "https://w3id.org/saref#humidity", - "hut": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dhut", - "implement": "https://w3id.org/saref#implement", - "ipAddress": { - "@id": "fiware:ipAddress", - "@type": "xsd:string" - }, - "irrSection": "https://w3id.org/saref#irrSection", - "irrSystem": "https://w3id.org/saref#irrSystem", - "isicV4": { - "@id": "schema:isicV4", - "@type": "xsd:string" - }, - "jobTitle": { - "@id": "schema:jobTitle", - "@type": "xsd:string" - }, - "location": "https://w3id.org/saref#location", - "macAddress": { - "@id": "fiware:macAddress", - "@type": "xsd:string" - }, - "mcc": { - "@id": "fiware:mcc", - "@type": "xsd:string" - }, - "meter": "https://w3id.org/saref#meter", - "milking": "https://w3id.org/saref#milking", - "mnc": { - "@id": "fiware:mnc", - "@type": "xsd:string" - }, - "motion": "https://w3id.org/saref#motion", - "movementActivity": "https://w3id.org/saref#movementActivity", - "multimedia": "https://w3id.org/saref#multimedia", - "name": { - "@id": "schema:name", "@type": "xsd:string" - }, - "network": "https://w3id.org/saref#network", - "occupancy": "https://w3id.org/saref#occupancy", - "occupier": { - "@id": "fiware:occupier", - "@type": "@id" - }, - "openingHours": { - "@id": "fiware:openingHours", - "@type": "xsd:array" - }, - "osVersion": { - "@id": "fiware:osVersion", - "@type": "xsd:string" - }, - "owner": { - "@id": "fiware:owner", - "@type": "@id" - }, - "precipitation": "https://w3id.org/saref#precipitation", - "pressure": "https://w3id.org/saref#pressure", - "provider": { - "@id": "fiware:provider", - "@type": "xsd:string" - }, - "refDeviceModel": { - "@id": "fiware:refDeviceModel", - "@type": "@id" - }, - "refMap": { - "@id": "fiware:refMap", - "@type": "xs:anyURI" - }, - "rssi": { - "@id": "fiware:rssi", - "@type": "xsd:string" - }, - "sensor": "https://w3id.org/saref#sensor", - "serialNumber": { - "@id": "fiware:serialNumber", - "@type": "xsd:string" - }, - "service": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dservice", - "shed": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dshed", - "softwareVersion": { - "@id": "fiware:softwareVersion", - "@type": "xsd:string" - }, - "soilMoisture": "https://w3id.org/saref#soilMoisture", - "solarRadiation": "https://w3id.org/saref#solarRadiation", - "source": { - "@id": "fiware:source", - "@type": "xsd:string" - }, - "stable": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dstable", - "sty": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dsty", - "supportedProtocol": { - "@id": "fiware:supportedProtocol", - "@type": "@vocab" - }, - "taxID": { - "@id": "schema:taxID", - "@type": "xsd:string" - }, - "telephone": { - "@id": "schema:telephone", - "@type": "xsd:string" - }, - "temperature": "https://w3id.org/saref#temperature", - "transformer_tower": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dtransformer_tower", - "value": { - "@id": "fiware:value", - "@type": "xsd:string" - }, - "vatID": { - "@id": "schema:vatID", - "@type": "xsd:string" - }, - "waterConsumption": "https://w3id.org/saref#waterConsumption", - "water_tower": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dwater_tower", - "weatherConditions": "https://w3id.org/saref#weatherConditions", - "weight": "https://w3id.org/saref#weight", - "windDirection": "https://w3id.org/saref#windDirection", - "windSpeed": "https://w3id.org/saref#windSpeed", - "state": "https://saref.etsi.org/core/hasState", - "heartRate": "https://purl.bioontology.org/ontology/MESH/D006339", - "status": "https://saref.etsi.org/core/status", - "product": { - "@id": "fiware:refObject", - "@type": "@id" - }, - - "worker": { - "@id": "fiware:refAgent", - "@type": "@id" - }, - "field": { - "@id": "fiware:refTarget", - "@type": "@id" - }, - "on": "https://w3id.org/saref#on", - "off": "https://w3id.org/saref#off", - "verified": "fiware:verified", - "species": "fiware:species", - "sex": "fiware:sex", - "legalID": "fiware:legalID", - "City": "fiware:City" - }, - "@graph": [ - { - "@id": "fiware:Building", - "@type": "rdfs:Class", - "rdfs:comment": [ - { - "@language": "en", - "@value": "" - } - ], - "rdfs:label": [ - { - "@language": "en", - "@value": "Building" - } - ], - "rdfs:subClassOf": { - "@id": "schema:Thing" - } - }, - { - "@id": "fiware:TemperatureSensor", - "@type": "rdfs:Class", - "rdfs:comment": [ - { - "@language": "en", - "@value": "A device that consists of a sensor, has category `saref:Sensor` and is used for the purpose of sensing temperature`." - } - ], - "rdfs:label": [ - { - "@language": "en", - "@value": "TemperatureSensor" - } - ], - "rdfs:subClassOf": { - "@id": "schema:Thing" - } - }, - { - "@id": "fiware:FillingLevelSensor", - "@type": "rdfs:Class", - "rdfs:comment": [ - { - "@language": "en", - "@value": "A device that consists of a sensor, has category `saref:Sensor` and is used for the purpose of sensing filling Level." - } - ], - "rdfs:label": [ - { - "@language": "en", - "@value": "FillingLevelSensor" - } - ], - "rdfs:subClassOf": { - "@id": "schema:Thing" - } - }, - { - "@id": "fiware:Person", - "@type": "rdfs:Class", - "rdfs:comment": [ - { - "@language": "en", - "@value": "" - } - ], - "rdfs:label": [ - { - "@language": "en", - "@value": "Person" - } - ], - "rdfs:subClassOf": { - "@id": "schema:Thing" - } - }, - { - "@id": "fiware:temperature", - "@type": "ngsi-ld:Property", - "rdfs:comment": [ - { - "@language": "en", - "@value": "Property related to some measurements that are characterized by a certain value that is measured in a temperature unit (degree_Celsius, degree_Fahrenheit, or degree_kelvin)" - } - ], - "rdfs:label": [ - { - "@language": "en", - "@value": "temperature" - } - ] - }, - { - "@id": "fiware:fillingLevel", - "@type": "ngsi-ld:Property", - "rdfs:comment": [ - { - "@language": "en", - "@value": "Property related to some measurements that are characterized by a certain value that is a filling level." - } - ], - "rdfs:label": [ - { - "@language": "en", - "@value": "fillingLevel" - } - ] - }, - { - "@id": "fiware:temperature", - "@type": "ngsi-ld:Property", - "rdfs:comment": [ - { - "@language": "en", - "@value": "Property related to some measurements that are characterized by a certain value that is measured in a temperature unit (degree_Celsius, degree_Fahrenheit, or degree_kelvin)" - } - ], - "rdfs:label": [ - { - "@language": "en", - "@value": "temperature" - } - ] - }, - { - "@id": "fiware:fillingLevel", - "@type": "ngsi-ld:Property", - "rdfs:comment": [ - { - "@language": "en", - "@value": "Property related to some measurements that are characterized by a certain value that is a filling level." - } - ], - "rdfs:label": [ - { - "@language": "en", - "@value": "fillingLevel" - } - ] - } - ] -} diff --git a/data-models/ngsi-context.jsonld b/data-models/ngsi-context.jsonld deleted file mode 100644 index 3befa99..0000000 --- a/data-models/ngsi-context.jsonld +++ /dev/null @@ -1,139 +0,0 @@ -{ - "@context": { - "type": "@type", - "id": "@id", - "ngsi-ld": "https://uri.etsi.org/ngsi-ld/", - "fiware": "https://uri.fiware.org/ns/dataModels#", - "schema": "https://schema.org/", - "tutorial": "https://ngsi-ld-tutorials.readthedocs.io/en/latest/datamodels.html#", - "Building": "fiware:Building", - "Device": "fiware:Device", - "Animal": "fiware:Animal", - "Female": "schema:Female", - "FillingLevelSensor": "tutorial:FillingLevelSensor", - "Herbicide": "tutorial:Product", - "HVAC": "https://w3id.org/saref#HVAC", - "Male": "schema:Male", - "PartField": "tutorial:PartField", - "Person": "fiware:Person", - "SoilSensor": "tutorial:SoilSensor", - "TemperatureSensor": "tutorial:TemperatureSensor", - "Task": "fiware:Activity", - "Tractor": "tutorial:Tractor", - "Water": "tutorial:Water", - "actuator": "https://w3id.org/saref#actuator", - "additionalName": "schema:additionalName", - "address": "schema:address", - "airPollution": "https://w3id.org/saref#airPollution", - "atmosphericPressure": "https://w3id.org/saref#atmosphericPressure", - "barn": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dbarn", - "batteryLevel": "fiware:batteryLevel", - "category": "fiware:category", - "configuration": "fiware:configuration", - "conservatory": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dconservatory", - "containedInPlace": "fiware:containedInPlace", - "controlledAsset": "fiware:controlledAsset", - "controlledProperty": "fiware:controlledProperty", - "cowshed": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dcowshed", - "dataProvider": "fiware:dataProvider", - "dateCreated": "fiware:dateCreated", - "dateFirstUsed": "fiware:dateFirstUsed", - "dateInstalled": "fiware:dateInstalled", - "dateLastCalibration": "fiware:dateLastCalibration", - "dateLastValueReported": "fiware:dateLastValueReported", - "dateManufactured": "fiware:dateManufactured", - "dateModified": "fiware:dateModified", - "depth": "https://w3id.org/saref#depth", - "description": "ngsi-ld:description", - "deviceState": "fiware:deviceState", - "digester": "https://wiki.openstreetmap.org/wiki/Tag:building%3Ddigester", - "eatingActivity": "https://w3id.org/saref#eatingActivity", - "email": "schema:email", - "endgun": "https://w3id.org/saref#endgun", - "familyName": "schema:familyName", - "farm": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dfarm", - "farm_auxiliary": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dfarm_auxiliary", - "faxNumber": "schema:faxNumber", - "filling": "https://w3id.org/saref#fillingLevel", - "firmwareVersion": "fiware:firmwareVersion", - "floorsAboveGround": "fiware:floorsAboveGround", - "floorsBelowGround": "fiware:floorsBelowGround", - "gender": "schema:gender", - "givenName": "schema:givenName", - "greenhouse": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dgreenhouse", - "hangar": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dhangar", - "hardwareVersion": "fiware:hardwareVersion", - "honorificPrefix": "schema:honorificPrefix", - "honorificSuffix": "schema:honorificSuffix", - "humidity": "https://w3id.org/saref#humidity", - "hut": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dhut", - "implement": "https://w3id.org/saref#implement", - "ipAddress": "fiware:ipAddress", - "irrSection": "https://w3id.org/saref#irrSection", - "irrSystem": "https://w3id.org/saref#irrSystem", - "isicV4": "schema:isicV4", - "jobTitle": "schema:jobTitle", - "location": "https://w3id.org/saref#location", - "macAddress": "fiware:macAddress", - "mcc": "fiware:mcc", - "meter": "https://w3id.org/saref#meter", - "milking": "https://w3id.org/saref#milking", - "mnc": "fiware:mnc", - "motion": "https://w3id.org/saref#motion", - "movementActivity": "https://w3id.org/saref#movementActivity", - "multimedia": "https://w3id.org/saref#multimedia", - "name": "schema:name", - "network": "https://w3id.org/saref#network", - "observedAt": "ngsi-ld:observedAt", - "occupancy": "https://w3id.org/saref#occupancy", - "occupier": "fiware:occupier", - "openingHours": "fiware:openingHours", - "osVersion": "fiware:osVersion", - "owner": "fiware:owner", - "precipitation": "https://w3id.org/saref#precipitation", - "pressure": "https://w3id.org/saref#pressure", - "providedBy": "fiware:providedBy", - "provider": "fiware:provider", - "refDeviceModel": "fiware:refDeviceModel", - "refMap": "fiware:refMap", - "rssi": "fiware:rssi", - "sensor": "https://w3id.org/saref#sensor", - "serialNumber": "fiware:serialNumber", - "service": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dservice", - "shed": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dshed", - "softwareVersion": "fiware:softwareVersion", - "soilMoisture": "https://w3id.org/saref#soilMoisture", - "solarRadiation": "https://w3id.org/saref#solarRadiation", - "source": "fiware:source", - "stable": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dstable", - "sty": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dsty", - "supportedProtocol": "fiware:supportedProtocol", - "taxID": "schema:taxID", - "telephone": "schema:telephone", - "temperature": "https://w3id.org/saref#temperature", - "transformer_tower": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dtransformer_tower", - "unitCode": "ngsi-ld:unitCode", - "value": "fiware:value", - "vatID": "schema:vatID", - "waterConsumption": "https://w3id.org/saref#waterConsumption", - "water_tower": "https://wiki.openstreetmap.org/wiki/Tag:building%3Dwater_tower", - "weatherConditions": "https://w3id.org/saref#weatherConditions", - "weight": "https://w3id.org/saref#weight", - "windDirection": "https://w3id.org/saref#windDirection", - "windSpeed": "https://w3id.org/saref#windSpeed", - "status": "https://saref.etsi.org/core/status", - "state": "https://saref.etsi.org/core/hasState", - "heartRate": "https://purl.bioontology.org/ontology/MESH/D006339", - "product": "fiware:refObject", - "worker": "fiware:refAgent", - "field": "fiware:refTarget", - - "on": "https://w3id.org/saref#on", - "off": "https://w3id.org/saref#off", - "verified": "fiware:verified", - "species": "fiware:species", - "sex": "fiware:sex", - "legalID": "fiware:legalID", - "City": "fiware:City" - } -} diff --git a/docker-compose/common.yml b/docker-compose/common.yml deleted file mode 100644 index fa085c6..0000000 --- a/docker-compose/common.yml +++ /dev/null @@ -1,73 +0,0 @@ -# WARNING: Do not deploy this tutorial configuration directly to a production environment -# -# The tutorial docker-compose files have not been written for production deployment and will not -# scale. A proper architecture has been sacrificed to keep the narrative focused on the learning -# goals, they are just used to deploy everything onto a single Docker machine. All FIWARE components -# are running at full debug and extra ports have been exposed to allow for direct calls to services. -# They also contain various obvious security flaws - passwords in plain text, no load balancing, -# no use of HTTPS and so on. -# -# This is all to avoid the need of multiple machines, generating certificates, encrypting secrets -# and so on, purely so that a single docker-compose file can be read as an example to build on, -# not use directly. -# -# When deploying to a production environment, please refer to the Helm Repository -# for FIWARE Components in order to scale up to a proper architecture: -# -# see: https://github.com/FIWARE/helm-charts/ -# -version: "3.8" -services: - # @context file is served from here - ld-context: - labels: - org.fiware: 'tutorial' - image: httpd:alpine - hostname: context - container_name: fiware-ld-context - ports: - - "3004:80" - volumes: - - data-models:/usr/local/apache2/htdocs/ - healthcheck: - test: (wget --server-response --spider --quiet http://ld-context/ngsi-context.jsonld 2>&1 | awk 'NR==1{print $$2}'| grep -q -e "200") || exit 1 - - # Databases - mongo-db: - labels: - org.fiware: 'tutorial' - image: mongo:${MONGO_DB_VERSION} - hostname: mongo-db - container_name: db-mongo - expose: - - "${MONGO_DB_PORT}" - ports: - - "${MONGO_DB_PORT}:${MONGO_DB_PORT}" # localhost:27017 - networks: - - default - volumes: - - mongo-db:/data/db - - mongo-config:/data/configdb - healthcheck: - test: | - host=`hostname --ip-address || echo '127.0.0.1'`; - mongo --quiet $host/test --eval 'quit(db.runCommand({ ping: 1 }).ok ? 0 : 2)' && echo 0 || echo 1 - interval: 5s - -networks: - default: - labels: - org.fiware: 'tutorial' - ipam: - config: - - subnet: 172.18.1.0/24 - -volumes: - mongo-db: ~ - mongo-config: ~ - data-models: - driver: local - driver_opts: - type: none - o: bind - device: ${PWD}/data-models \ No newline at end of file diff --git a/docker-compose/orion-ld.yml b/docker-compose/orion-ld.yml deleted file mode 100644 index 69737df..0000000 --- a/docker-compose/orion-ld.yml +++ /dev/null @@ -1,39 +0,0 @@ -# WARNING: Do not deploy this tutorial configuration directly to a production environment -# -# The tutorial docker-compose files have not been written for production deployment and will not -# scale. A proper architecture has been sacrificed to keep the narrative focused on the learning -# goals, they are just used to deploy everything onto a single Docker machine. All FIWARE components -# are running at full debug and extra ports have been exposed to allow for direct calls to services. -# They also contain various obvious security flaws - passwords in plain text, no load balancing, -# no use of HTTPS and so on. -# -# This is all to avoid the need of multiple machines, generating certificates, encrypting secrets -# and so on, purely so that a single docker-compose file can be read as an example to build on, -# not use directly. -# -# When deploying to a production environment, please refer to the Helm Repository -# for FIWARE Components in order to scale up to a proper architecture: -# -# see: https://github.com/FIWARE/helm-charts/ -# -version: "3.8" -services: - - # Orion is the context broker - orion: - labels: - org.fiware: 'tutorial' - platform: linux/amd64 - image: quay.io/fiware/orion-ld:${ORION_LD_VERSION} - hostname: orion - container_name: fiware-orion - depends_on: - - mongo-db - networks: - - default - ports: - - ${EXPOSED_PORT:-1026}:${ORION_LD_PORT:-1026} - command: -dbhost mongo-db -logLevel DEBUG -forwarding -experimental - healthcheck: - test: curl --fail -s http://orion:${ORION_LD_PORT}/version || exit 1 - interval: 5s diff --git a/docker-compose/scorpio-aaio.yml b/docker-compose/scorpio-aaio.yml deleted file mode 100644 index b905a47..0000000 --- a/docker-compose/scorpio-aaio.yml +++ /dev/null @@ -1,85 +0,0 @@ -# WARNING: Do not deploy this tutorial configuration directly to a production environment -# -# The tutorial docker-compose files have not been written for production deployment and will not -# scale. A proper architecture has been sacrificed to keep the narrative focused on the learning -# goals, they are just used to deploy everything onto a single Docker machine. All FIWARE components -# are running at full debug and extra ports have been exposed to allow for direct calls to services. -# They also contain various obvious security flaws - passwords in plain text, no load balancing, -# no use of HTTPS and so on. -# -# This is all to avoid the need of multiple machines, generating certificates, encrypting secrets -# and so on, purely so that a single docker-compose file can be read as an example to build on, -# not use directly. -# -# When deploying to a production environment, please refer to the Helm Repository -# for FIWARE Components in order to scale up to a proper architecture: -# -# see: https://github.com/FIWARE/helm-charts/ -# -version: "3.9" - -services: - zookeeper: - labels: - org.fiware: 'tutorial' - image: zookeeper - hostname: zookeeper - container_name: zookeeper - networks: - - default - ports: - - "2181" - logging: - driver: none - kafka: - labels: - org.fiware: 'tutorial' - image: bitnami/kafka - hostname: kafka - container_name: kafka - networks: - - default - ports: - - "9092" - environment: - KAFKA_ADVERTISED_HOST_NAME: kafka - KAFKA_ZOOKEEPER_CONNECT: zookeeper:2181 - KAFKA_ADVERTISED_PORT: 9092 - KAFKA_LOG_RETENTION_MS: 10000 - KAFKA_LOG_RETENTION_CHECK_INTERVAL_MS: 5000 - ALLOW_PLAINTEXT_LISTENER: "yes" - volumes: - - /var/run/docker.sock:/var/run/docker.sock - depends_on: - - zookeeper - logging: - driver: none - postgres: - labels: - org.fiware: 'tutorial' - image: postgis/postgis - hostname: postgres - container_name: db-postgres - networks: - - default - ports: - - "5432" - environment: - POSTGRES_USER: ngb - POSTGRES_PASSWORD: ngb - POSTGRES_DB: ngb - logging: - driver: none - scorpio: - labels: - org.fiware: 'tutorial' - image: scorpiobroker/all-in-one-runner:java-kafka-${SCORPIO_VERSION} - hostname: scorpio - container_name: fiware-scorpio - networks: - - default - ports: - - ${EXPOSED_PORT:-1026}:${SCORPIO_PORT:-9090} - depends_on: - - postgres - - kafka diff --git a/docker-compose/stellio.yml b/docker-compose/stellio.yml deleted file mode 100644 index 462a6ff..0000000 --- a/docker-compose/stellio.yml +++ /dev/null @@ -1,107 +0,0 @@ -version: '3.9' -services: - api-gateway: - container_name: stellio-api-gateway - hostname: stellio - labels: - org.fiware: 'tutorial' - image: stellio/stellio-api-gateway:${STELLIO_DOCKER_TAG} - environment: - - SPRING_PROFILES_ACTIVE=docker - ports: - - ${EXPOSED_PORT:-1026}:${STELLIO_PORT:-9090} - - search-service: - container_name: stellio-search-service - labels: - org.fiware: 'tutorial' - image: stellio/stellio-search-service:${STELLIO_DOCKER_TAG} - environment: - - SPRING_PROFILES_ACTIVE=docker - - SPRING_R2DBC_URL=r2dbc:postgresql://postgres/stellio_search - - SPRING_FLYWAY_URL=jdbc:postgresql://postgres/stellio_search - - SPRING_R2DBC_USERNAME=stellio - - SPRING_R2DBC_PASSWORD=stellio_password - - APPLICATION_AUTHENTICATION_ENABLED=false - ports: - - 8083:8083 - restart: always - depends_on: - postgres: - condition: service_healthy - kafka: - condition: service_started - - subscription-service: - container_name: stellio-subscription-service - labels: - org.fiware: 'tutorial' - image: stellio/stellio-subscription-service:${STELLIO_DOCKER_TAG} - environment: - - SPRING_PROFILES_ACTIVE=docker - - SPRING_R2DBC_URL=r2dbc:postgresql://postgres/stellio_subscription - - SPRING_FLYWAY_URL=jdbc:postgresql://postgres/stellio_subscription - - SPRING_R2DBC_USERNAME=stellio - - SPRING_R2DBC_PASSWORD=stellio_password - - APPLICATION_AUTHENTICATION_ENABLED=false - ports: - - 8085:8084 - restart: always - depends_on: - postgres: - condition: service_healthy - kafka: - condition: service_started - - kafka: - labels: - org.fiware: 'tutorial' - image: confluentinc/cp-kafka:7.3.1 - container_name: kafka - ports: - - 29092:29092 - restart: always - environment: - KAFKA_BROKER_ID: 1 - KAFKA_LISTENER_SECURITY_PROTOCOL_MAP: CONTROLLER:PLAINTEXT,PLAINTEXT:PLAINTEXT,PLAINTEXT_HOST:PLAINTEXT - KAFKA_ADVERTISED_LISTENERS: PLAINTEXT://kafka:9092,PLAINTEXT_HOST://localhost:29092 - KAFKA_OFFSETS_TOPIC_REPLICATION_FACTOR: 1 - KAFKA_PROCESS_ROLES: 'broker,controller' - KAFKA_NODE_ID: 1 - KAFKA_CONTROLLER_QUORUM_VOTERS: '1@kafka:29093' - KAFKA_LISTENERS: CONTROLLER://kafka:29093,PLAINTEXT://kafka:9092,PLAINTEXT_HOST://0.0.0.0:29092 - KAFKA_INTER_BROKER_LISTENER_NAME: 'PLAINTEXT' - KAFKA_CONTROLLER_LISTENER_NAMES: 'CONTROLLER' - KAFKA_LOG4J_ROOT_LOGLEVEL: INFO - volumes: - - ./stellio/kafka/update_run.sh:/tmp/update_run.sh - command: "bash -c 'if [ ! -f /tmp/update_run.sh ]; then echo \"ERROR: Did you forget the update_run.sh file that came with this docker-compose.yml file?\" && exit 1 ; else /tmp/update_run.sh && /etc/confluent/docker/run ; fi'" - - - # Databases - postgres: - labels: - org.fiware: 'tutorial' - image: stellio/stellio-timescale-postgis:${STELLIO_TIMESCALE_POSTGIS} - - hostname: postgres - container_name: db-postgres - environment: - - POSTGRES_USER=stellio - - POSTGRES_PASS=stellio_password - - POSTGRES_DBNAME=stellio_search,stellio_subscription - - POSTGRES_MULTIPLE_EXTENSIONS=postgis,timescaledb,pgcrypto - - ACCEPT_TIMESCALE_TUNING=TRUE - ports: - - 5432:5432 - volumes: - - postgres-db:/var/lib/postgresql - healthcheck: - test: ["CMD-SHELL", "pg_isready -h localhost -U stellio"] - interval: 10s - timeout: 5s - retries: 20 - start_period: 10s - -volumes: - postgres-db: ~ diff --git a/docker-compose/stellio/kafka/update_run.sh b/docker-compose/stellio/kafka/update_run.sh deleted file mode 100755 index 18de790..0000000 --- a/docker-compose/stellio/kafka/update_run.sh +++ /dev/null @@ -1,11 +0,0 @@ -#!/bin/sh - -# Docker workaround: Remove check for KAFKA_ZOOKEEPER_CONNECT parameter -sed -i '/KAFKA_ZOOKEEPER_CONNECT/d' /etc/confluent/docker/configure - -# Docker workaround: Ignore cub zk-ready -sed -i 's/cub zk-ready/echo ignore zk-ready/' /etc/confluent/docker/ensure - -# KRaft required step: Format the storage directory with a new cluster ID -echo "kafka-storage format --ignore-formatted -t $(kafka-storage random-uuid) -c /etc/kafka/kafka.properties" >> /etc/confluent/docker/ensure - diff --git a/import-data b/import-data deleted file mode 100644 index e5dcbda..0000000 --- a/import-data +++ /dev/null @@ -1,107 +0,0 @@ -#!/bin/bash -# -# curl commands to reload the data from the previous tutorial -# -# - -set -e - -echo -e "⏳ Loading context data in \033[1mNGSI-LD\033[0m format" -echo -e " - all entity data models are defined referencing the" -echo -e " \033[1m"${TUTORIAL_DATA_MODELS_CONTEXT}"\033[0m JSON-LD context" -echo -e "Creating two cities" -# -# Create two citie entities. -# -curl -s -o /dev/null -X POST 'http://'"${CONTEXT_BROKER}"'/ngsi-ld/v1/entityOperations/upsert' \ --H 'Content-Type: application/json' \ --H 'Link: <'"${TUTORIAL_DATA_MODELS_CONTEXT}"'>; rel="http://www.w3.org/ns/json-ld#context"; type="application/ld+json"' \ --H 'Accept: application/ld+json' \ ---data-raw '[ - { - "id": "urn:ngsi-ld:City:001", - "type": "City", - "temperature": { - "type": "Property", - "value": 25, - "unitCode": "CEL", - "observedAt": "2022-06-30T00:00:00.000Z" - }, - "location": { - "type": "GeoProperty", - "value": { - "type": "Point", - "coordinates": [ - 28.955, - 41.0136 - ] - } - }, - "population": { - "type": "Property", - "value": 15840900, - "observedAt": "2022-12-31T00:00:00.000Z" - }, - "address": { - "type": "Property", - "value": { - "streetAddress": "Kanlıca İskele Meydanı", - "addressRegion": "İstanbul", - "addressLocality": "Beşiktaş", - "postalCode": "12345" - } - }, - "name": { - "type": "LanguageProperty", - "languageMap": { - "el": "Κωνσταντινούπολις", - "en": "Constantinople", - "tr": "İstanbul" - } - }, - "runBy": { - "type": "Relationship", - "object": "urn:ngsi-ld:Adminstration:Cumhuriyet_Halk_Partisi" - } - }, - { - "id": "urn:ngsi-ld:City:002", - "type": "City", - "temperature": { - "value": 25, - "unitCode": "CEL", - "observedAt": "2022-06-30T00:00:00.000Z" - }, - "address": { - "value": { - "streetAddress": "Viale di Valle Aurelia", - "addressRegion": "Lazio", - "addressLocality": "Roma", - "postalCode": "00138" - } - }, - "location": { - "type": "Point", - "coordinates": [ - 12.482, - 41.893 - ] - }, - "population": { - "value": 4342212, - "observedAt": "2021-01-01T00:00:00.000Z" - }, - "name": { - "languageMap": { - "el": "Ρώμη", - "en": "Rome", - "it": "Roma" - } - }, - "runBy": { - "object": "urn:ngsi-ld:Adminstration:Partito_Democratico" - } - } -]' - -echo -e " \033[1;32mdone\033[0m" diff --git a/services b/services index cdeb706..d1dff8f 100755 --- a/services +++ b/services @@ -1,273 +1,8 @@ #!/bin/bash # # Command Line Interface to start all services associated with the Tutorial -# For this tutorial the commands are merely a convenience script to run docker or docker-compose # -# Each services script can be run using either docker-compose (the external tool with the hyphen -) -# or docker compose (the newer version directly bundled with Docker with a space ) -# -# if you start up with the following command: -# -# ./services start legacy -# -# This will force the script to use docker-compose which may be more reliable in -# some cases (or if an older version of Docker is being used) set -e -STELLIO="http://stellio:8080/actuator/health" -SCORPIO="http://scorpio:9090/scorpio/" -ORION="http://orion:1026/version" -STELLIO="http://localhost:8080/actuator/health" -CONTEXT="http://context/ngsi-context.jsonld" -CORE_CONTEXT="https://uri.etsi.org/ngsi-ld/v1/ngsi-ld-core-context.jsonld" - -dockerCmd="docker compose" -if (( $# == 2 )); then - dockerCmd="docker-compose" -fi - -if (( $# < 1 )); then - echo "Illegal number of parameters" - echo "usage: services [create|orion|scorpio|stellio|stop]" - exit 1 -fi - -pause(){ - printf " " - count="$1" - [ "$count" -gt 59 ] && printf "Waiting one minute " || printf " Waiting a few seconds "; - while [ "$count" -gt 0 ] - do - printf "." - sleep 3 - count=$((count - 3)) - done - echo "" -} - -getHeartbeat(){ - eval "response=$(docker run --network fiware_default --rm quay.io/curl/curl -s -o /dev/null -w "%{http_code}" "$1")" -} - -waitForOrion () { - echo -e "\n⏳ Waiting for \033[1;34mOrion-LD\033[0m to be available\n" - getHeartbeat "${ORION}" - while [ "${response}" -eq 000 ] - do - echo -e "\nContext Broker HTTP state: ${response} (waiting for 200)" - pause 6 - getHeartbeat "${ORION}" - done -} - -waitForMongo () { - echo -e "\n⏳ Waiting for \033[1mMongoDB\033[0m to be available\n" - while ! [ `docker inspect --format='{{.State.Health.Status}}' db-mongo` == "healthy" ] - do - sleep 1 - done -} - -waitForScorpio () { - echo -e "\n⏳ Waiting for \033[1;34mScorpio\033[0m to respond\n" - getHeartbeat "${SCORPIO}" - while [ "${response}" -eq 000 ] - do - echo -e "Context Broker HTTP state: ${response} (waiting for 500)" - pause 60 - getHeartbeat "${SCORPIO}" - done -} - -waitForStellio () { - echo -e "\n⏳ Waiting for \033[1;34mStellio\033[0m to respond\n" - waitSeconds=30 - while [ `docker run --network fiware_default --rm quay.io/curl/curl -s -o /dev/null -w %{http_code} 'http://stellio:8080/ngsi-ld/v1/entities/?type=X'` -eq 000 ] - do - echo -e "Context Broker HTTP state: " `curl -s -o /dev/null -w %{http_code} 'http://localhost:8080/ngsi-ld/v1/entities/?type=X'` " (waiting for 500)" - echo -e "Waiting for ${waitSeconds} seconds ..." - sleep ${waitSeconds} - done - echo -e "\n⏳ Waiting for all \033[1;34mStellio\033[0m services to be available\n" - while [ `docker run --network fiware_default --rm quay.io/curl/curl -s -o /dev/null -w %{http_code} 'http://stellio:8080/ngsi-ld/v1/entities/?type=X'` -eq 500 ] - do - echo -e "Context Broker HTTP state: " `curl -s -o /dev/null -w %{http_code} 'http://localhost:8080/ngsi-ld/v1/entities/?type=X'` " (waiting for 200)" - echo -e "Waiting for ${waitSeconds} seconds ..." - sleep ${waitSeconds} - done -} - -waitForCoreContext () { - echo -e "\n⏳ Checking availability of \033[1m core @context\033[0m from ETSI\n" - eval "response=$(docker run --rm quay.io/curl/curl -s -o /dev/null -w "%{http_code}" "$CORE_CONTEXT")" - while [ "${response}" -eq 000 ] - do - echo -e "\n@context HTTP state: ${response} (waiting for 200)" - pause 3 - eval "response=$(docker run --rm quay.io/curl/curl -s -o /dev/null -w "%{http_code}" "$CORE_CONTEXT")" - done -} - -waitForUserContext () { - echo -e "\n⏳ Waiting for user \033[1m@context\033[0m to be available\n" - getHeartbeat "${CONTEXT}" - while [ "${response}" -eq 000 ] - do - echo -e "\n@context HTTP state: ${response} (waiting for 200)" - pause 3 - getHeartbeat "${CONTEXT}" - done -} - - -addDatabaseIndex () { - printf "Adding appropriate \033[1mMongoDB\033[0m indexes for \033[1;34mOrion\033[0m ..." - docker exec db-mongo mongo --eval ' - conn = new Mongo();db.createCollection("orion"); - db = conn.getDB("orion"); - db.createCollection("entities"); - db.entities.createIndex({"_id.servicePath": 1, "_id.id": 1, "_id.type": 1}, {unique: true}); - db.entities.createIndex({"_id.type": 1}); - db.entities.createIndex({"_id.id": 1});' > /dev/null - - docker exec db-mongo mongo --eval ' - conn = new Mongo();db.createCollection("orion-openiot"); - db = conn.getDB("orion-openiot"); - db.createCollection("entities"); - db.entities.createIndex({"_id.servicePath": 1, "_id.id": 1, "_id.type": 1}, {unique: true}); - db.entities.createIndex({"_id.type": 1}); - db.entities.createIndex({"_id.id": 1});' > /dev/null - echo -e " \033[1;32mdone\033[0m" -} - -loadData () { - waitForUserContext - export CONTEXT_BROKER="$1" - docker run --rm -v $(pwd)/import-data:/import-data \ - --network fiware_default \ - -e CONTEXT_BROKER=${CONTEXT_BROKER} \ - -e TUTORIAL_DATA_MODELS_CONTEXT="http://context/ngsi-context.jsonld" \ - --entrypoint /bin/ash quay.io/curl/curl /import-data - echo "" -} - -stoppingContainers () { - CONTAINERS=$(docker ps --filter "label=org.fiware=tutorial" -aq) - if [[ -n $CONTAINERS ]]; then - echo "Stopping containers" - docker rm -f $CONTAINERS || true - fi - VOLUMES=$(docker volume ls -qf dangling=true) - if [[ -n $VOLUMES ]]; then - echo "Removing old volumes" - docker volume rm $VOLUMES || true - fi - NETWORKS=$(docker network ls --filter "label=org.fiware=tutorial" -q) - if [[ -n $NETWORKS ]]; then - echo "Removing tutorial networks" - docker network rm $NETWORKS || true - fi -} - -displayServices () { - echo "" - docker ps --format "table {{.Names}}\t{{.Status}}\t{{.Ports}}" --filter name="$1" - echo "" -} - -waitForMongo () { - echo -e "\n⏳ Waiting for \033[1mMongoDB\033[0m to be available\n" - while ! [ `docker inspect --format='{{.State.Health.Status}}' db-mongo` == "healthy" ] - do - sleep 1 - done -} - -waitForOrion () { - echo -e "\n⏳ Waiting for \033[1;34mOrion\033[0m to be available\n" - - while ! [ `docker inspect --format='{{.State.Health.Status}}' fiware-orion` == "healthy" ] - do - echo -e "Context Broker HTTP state: " `curl -s -o /dev/null -w %{http_code} 'http://localhost:1026/version'` " (waiting for 200)" - sleep 1 - done -} - - -export $(cat .env | grep "#" -v) -command="$1" -case "${command}" in - "help") - echo "usage: services [create|orion|scorpio|stellio|stop]" - ;; - "orion") - export $(cat .env | grep "#" -v) - stoppingContainers - waitForCoreContext - echo -e "Starting containers: \033[1;34mOrion\033[0m, \033[1mTutorial\033[0m and a \033[1mMongoDB\033[0m database." - echo -e "- \033[1;34mOrion\033[0m is the context broker" - echo -e "- Data models \033[1m@context\033[0m (Smart Farm) is supplied externally" - echo "" - ${dockerCmd} -f docker-compose/common.yml -f docker-compose/orion-ld.yml up -d --remove-orphans --renew-anon-volumes - displayServices "orion|fiware" - waitForMongo - addDatabaseIndex - waitForOrion - export CONTEXT_BROKER=orion:1026 - loadData orion:1026 - echo -e "\033[1;34m${command}\033[0m is now running and exposed on localhost:${EXPOSED_PORT}" - ;; - "scorpio") - export $(cat .env | grep "#" -v) - stoppingContainers - waitForCoreContext - echo -e "Starting containers: \033[1;34mScorpio\033[0m, \033[1mKafka\033[0m, \033[1mZookeeper\033[0m and a \033[1mPostgres\033[0m database, \033[1;36mIoT-Agent\033[0m, \033[1mTutorial\033[0m and a \033[1mMongoDB\033[0m database." - echo -e "- \033[1;34mScorpio\033[0m is the context broker" - echo -e "- Data models \033[1m@context\033[0m (Smart Farm) is supplied externally" - echo "" - ${dockerCmd} -f docker-compose/common.yml -f docker-compose/scorpio-aaio.yml up -d --remove-orphans --renew-anon-volumes - displayServices "scorpio|fiware" - waitForMongo - addDatabaseIndex - waitForScorpio - export CONTEXT_BROKER=scorpio:9090 - loadData scorpio:9090 - echo -e "\033[1;34m${command}\033[0m is now running and exposed on localhost:${EXPOSED_PORT}" - ;; - "stellio") - export $(cat .env | grep "#" -v) - stoppingContainers - waitForCoreContext - echo -e "Starting containers: \033[1;34mStellio\033[0m, \033[1mKafka\033[0m, \033[1mZookeeper\033[0m and a \033[1mPostgres\033[0m database, \033[1;36mIoT-Agent\033[0m, \033[1mTutorial\033[0m and a \033[1mMongoDB\033[0m database." - echo -e "- \033[1;34mStellio\033[0m is the context broker" - echo -e "- Data models \033[1m@context\033[0m (Smart Farm) is supplied externally" - echo "" - ${dockerCmd} -f docker-compose/common.yml -f docker-compose/stellio.yml up -d --remove-orphans --renew-anon-volumes - displayServices "stellio|fiware" - waitForMongo - addDatabaseIndex - waitForStellio - export CONTEXT_BROKER=stellio:8080 - loadData stellio:8080 - echo -e "\033[1;34m${command}\033[0m is now running and exposed on localhost:${EXPOSED_PORT}" - ;; - "stop") - export $(cat .env | grep "#" -v) - stoppingContainers - ;; - "start") - ./services ${CONTEXT_BROKER:=orion} $2 - ;; - "create") - export $(cat .env | grep "#" -v) - echo "Pulling Docker images" - docker pull curlimages/curl - ${dockerCmd} -f docker-compose/common.yml -f docker-compose/scorpio-aaio.yml -f docker-compose/orion-ld.yml -f docker-compose/stellio.yml pull - ;; - *) - echo "Command not Found." - echo "usage: services [create|orion|scorpio|stellio|stop]" - exit 127; - ;; -esac \ No newline at end of file +echo -e "Please checkout the \033[1;36mNGSI-LD\033[0m branch of this repository to run this tutorial."