# yaml-language-server: $schema=https://schemas.sourcemeta.com/openapi/v3.1/schema/2025-09-15.json openapi: 3.1.0 info: title: Edison Next Panorama - Integration API description: |- API standard di integrazione di *Edison Next Panorama* con sistemi esterni contact: name: API Support email: support@panorama.edisonnext.it version: 0.9.8 license: name: © 2025 - 2030 Copyright Edison Next Spa. All rights reserved url: https://edisonnext.it externalDocs: description: Edison Next Panorama - Specifiche di Integrazione v.1.0 url: https://panorama.edisonnext.it/ # security di default (richiesta anche per accedere ai dati in lettura) security: - panorama_consumer_api_key: [] #servers: # - url: https://panorama.edisonnext.it/api/v1 # description: Main (production) API server # - url: # description: Staging API server # - url: # description: Development API server tags: - name: Data Source description: operations for data sources - name: Type description: operations for data types - name: Entity description: operations to browse and manage entities - name: DataPoint description: Operations about the Data Point paths: /type: get: summary: Restituisce i Tipi di Entità definiti tags: [Type] operationId: getTypes responses: '200': description: successful operation content: application/json: schema: type: array items: $ref: '#/components/schemas/Type' post: summary: Crea un nuovo Tipo di Entità (admin only) tags: [Type] security: - panorama_administrator_api_key: [] requestBody: required: true content: application/json: schema: $ref: '#/components/schemas/Type' responses: '201': description: Tipo creato '422': description: Tipo non valido /type/{id}: get: summary: Restituisce un singolo Tipo di Entità operationId: getType tags: [Type] parameters: - in: path name: id required: true schema: type: string responses: '200': description: Tipo trovato content: application/json: schema: $ref: '#/components/schemas/Type' '404': description: Tipo non trovato put: summary: Modifica un Tipo esistente (admin only) tags: [Type] security: - panorama_administrator_api_key: [] parameters: - in: path name: id required: true schema: type: string requestBody: required: true content: application/json: schema: $ref: '#/components/schemas/Type' responses: '200': description: Tipo aggiornato '404': description: Tipo non trovato '422': description: Tipo non valido delete: summary: Elimina un Tipo (senza istanze di elementi) esistente (admin only) tags: [Type] security: - panorama_administrator_api_key: [] parameters: - in: path name: id required: true schema: type: string responses: '204': description: Tipo eliminato '404': description: Tipo non trovato /source: get: summary: Restituisce le fonti dati disponibili tags: [Data Source] responses: '200': description: successful operation content: application/json: schema: type: array items: $ref: '#/components/schemas/Source' post: summary: Aggiunge una Fonte Dati (admin only) tags: [Data Source] security: - panorama_administrator_api_key: [] requestBody: required: true content: application/json: schema: $ref: '#/components/schemas/Source' responses: '201': description: Fonte Dati creata '422': description: Fonte Dati non valida /source/{id}: put: summary: Modifica una sorgente dati esistente (admin only) tags: [Data Source] security: - panorama_administrator_api_key: [] parameters: - in: path name: id required: true schema: type: string requestBody: required: true content: application/json: schema: $ref: '#/components/schemas/Source' responses: '200': description: Data Source aggiornata '404': description: Data Source non trovata '422': description: Data Source non valida delete: summary: Elimina una sorgente dati (vuota) esistente (admin only) tags: [Data Source] security: - panorama_administrator_api_key: [] parameters: - in: path name: id required: true schema: type: string responses: '204': description: Sorgente Dati eliminata /terminology: get: summary: Restituisce le Nomenclature definite tags: [Type] operationId: getTerminologies responses: '200': description: successful operation content: application/json: schema: type: array items: $ref: '#/components/schemas/Terminology' post: summary: Crea una nuova Nomenclatura (admin only) tags: [Type] security: - panorama_administrator_api_key: [] requestBody: required: true content: application/json: schema: $ref: '#/components/schemas/Terminology' responses: '201': description: Nomenclatura creata '422': description: Nomenclatura non valida /terminology/{id}: get: summary: Restituisce una singola Nomenclatura tags: [Type] parameters: - in: path name: id required: true schema: type: string responses: '200': description: Tipo trovato content: application/json: schema: $ref: '#/components/schemas/Type' '404': description: Nomenclatura non trovata put: summary: Modifica una Nomenclatura esistente (admin only) tags: [Type] security: - panorama_administrator_api_key: [] parameters: - in: path name: id required: true schema: type: string requestBody: required: true content: application/json: schema: $ref: '#/components/schemas/Terminology' responses: '200': description: Nomenclatura aggiornata '404': description: Nomenclatura non trovata '422': description: Nomenclatura non valida delete: summary: Elimina una Nomenclatura (senza riferimenti in qualche tipo) esistente (admin only) tags: [Type] security: - panorama_administrator_api_key: [] parameters: - in: path name: id required: true schema: type: string responses: '204': description: Nomenclatura eliminata '404': description: Nomenclatura non trovata /entity: get: summary: Ricerca di entità tags: [Entity] parameters: - name: type in: query description: Filter by entity type required: false explode: true schema: type: string - name: source in: query description: Filter by data source required: false explode: true schema: type: string - name: state in: query description: Filter by entity state required: false explode: true schema: type: string responses: '200': description: Lista di entità content: application/json: schema: type: array items: $ref: '#/components/schemas/Entity' post: summary: Crea una nuova entità tags: [Entity] security: - panorama_provider_api_key: [] requestBody: required: true content: application/json: schema: $ref: '#/components/schemas/Entity' responses: '422': description: Entità non valida '201': description: Entità creata /entity/{id}: get: summary: Ottiene una singola entità operationId: getEntity tags: [Entity] parameters: - in: path name: id required: true schema: type: string responses: '200': description: Entità trovata content: application/json: schema: $ref: '#/components/schemas/Entity' '404': description: Entità non trovata put: summary: Modifica un'entità esistente (escluso lo stato) tags: [Entity] security: - panorama_provider_api_key: [] parameters: - in: path name: id required: true schema: type: string requestBody: required: true content: application/json: schema: $ref: '#/components/schemas/Entity' responses: '200': description: Entità aggiornata '404': description: Entità non trovata '422': description: Entità non valida delete: summary: Elimina un'entità tags: [Entity] security: - panorama_provider_api_key: [] parameters: - in: path name: id required: true schema: type: string responses: '204': description: Entità eliminata '404': description: Entità non trovata /entity/{id}/dataPoint: get: summary: Ottiene il data point associato a un'entità operationId: getEntityDataPoint tags: [Entity] parameters: - in: path name: id required: true schema: type: string responses: '200': description: Data Point trovato content: application/json: schema: $ref: '#/components/schemas/DataPoint' '404': description: Data Point associato a Entità non trovato /state/{id}: put: summary: Modifica lo stato di un'Entità tags: [Entity] security: - panorama_provider_api_key: [] parameters: - in: path name: id required: true schema: type: string requestBody: required: true content: application/json: schema: type: string responses: '200': description: Stato Entità aggiornato '422': description: Stato Entità non valido '404': description: Entità non trovata /history/{id}: get: summary: Ottiene la storia delle variazioni di stato di un'Entità tags: [Entity] parameters: - in: path name: id description: l'ID dell'entità di cui ottenere la storia required: true schema: type: string responses: '200': description: Entità trovata content: application/json: schema: type: array items: type: object properties: timestamp: type: string format: date-time state: type: string examples: ['off', '22°C'] '404': description: Entità non trovata /dataPoint: get: summary: Elenco di tutti i dispositivi tags: [DataPoint] responses: '200': description: Lista di dispositivi content: application/json: schema: type: array items: $ref: '#/components/schemas/DataPoint' /dataPoint/{id}: get: summary: Ottiene informazioni su un singolo dispositivo tags: [DataPoint] parameters: - in: path name: id required: true schema: type: string responses: '200': description: Dispositivo trovato content: application/json: schema: $ref: '#/components/schemas/DataPoint' '404': description: Dispositivo non trovato /dataPoint/measures: get: summary: Ottiene tutte le misure in un range di date tags: [DataPoint] operationId: getMeasures parameters: - name: measurement_date_from in: query description: Filter by measurement date (from) required: false explode: true schema: type: string format: date-time - name: measurement_date_to in: query description: Filter by measurement date (to) required: false explode: true schema: type: string format: date-time responses: '200': description: Lista delle misure content: application/json: schema: type: array items: $ref: '#/components/schemas/Measure' /dataPoint/{id}/measures: get: summary: Ottiene tutte le misure da un Data Point tags: [DataPoint] operationId: getMeasuresByDataPoint parameters: - in: path name: id required: true schema: type: string - name: measurement_date_from in: query description: Filter by measurement date (from) required: false explode: true schema: type: string format: date-time - name: measurement_date_to in: query description: Filter by measurement date (to) required: false explode: true schema: type: string format: date-time responses: '200': description: Lista delle misure content: application/json: schema: type: array items: $ref: '#/components/schemas/Measure' /dataPoint/{id}/measures/last: get: summary: Ottieni ultima misura da un data point tags: [DataPoint] operationId: getMeasureByDataPoint parameters: - name: id in: path required: true schema: type: string responses: '200': description: Misura trovata content: application/json: schema: $ref: '#/components/schemas/Measure' '404': description: Nessuna Misura trovata /measurementType/{id}: get: summary: Restituisce un singolo tipo di misura operationId: getMeasurementTypeById tags: [DataPoint] parameters: - in: path name: id required: true schema: type: string responses: '200': description: Tipo di misura trovato content: application/json: schema: $ref: '#/components/schemas/MeasurementType' '404': description: Tipo di misura non trovato put: summary: Modifica un tipo di misura esistente (admin only) tags: [DataPoint] security: - panorama_administrator_api_key: [] parameters: - in: path name: id required: true schema: type: string requestBody: required: true content: application/json: schema: $ref: '#/components/schemas/MeasurementType' responses: '200': description: Tipo di misura aggiornato con successo '404': description: Tipo di misura non trovato '422': description: Tipo di misura non valido delete: summary: Elimina un tipo di misura esistente (admin only) tags: [DataPoint] security: - panorama_administrator_api_key: [] parameters: - in: path name: id required: true schema: type: string responses: '204': description: Tipo di misura eliminato con successo '404': description: Tipo di misura non trovato /measurementType: get: summary: Restituisce tutti i tipi di misura definiti tags: [DataPoint] operationId: getMeasurementTypes responses: '200': description: Operazione completata con successo content: application/json: schema: type: array items: $ref: '#/components/schemas/MeasurementType' post: summary: Crea un nuovo tipo di misura (admin only) tags: [DataPoint] security: - panorama_administrator_api_key: [] requestBody: required: true content: application/json: schema: $ref: '#/components/schemas/MeasurementType' responses: '201': description: Tipo di misura creato con successo '422': description: Tipo di misura non valido components: schemas: Terminology: type: object description: Nomenclatura di riferimento per i Tipi di Entità. Può essere interna o esterna (schema.gov.it, UCUM, Google Knowledge Graph) required: [id, name, syntax] properties: id: type: string format: uri description: Identificativo univoco della Nomenclatura (terminology) examples: - http://dati.beniculturali.it/cis name: type: string description: Nome canonico della Nomenclatura description: type: string description: Descrizione della Nomenclatura documentation: type: string format: uri description: Link alla documentazione della Nomenclatura examples: - 'https://schema.gov.it/' subject: type: string description: Soggetto titolare del Tipo examples: - 'Ministero per i Beni e le Attività Culturali' uri: type: string format: uri description: URI autoritativa della Nomenclatura examples: - http://dati.beniculturali.it/cis Type: type: object description: Tipi di entità, comprensivi di riferimento al nomenclatore e definizione della struttura del payload specifico required: [id, name, syntax] properties: id: type: string format: uri description: Identificativo univoco del Tipo di Entità examples: - http://dati.beniculturali.it/cis/CulturalInstituteOrSite name: type: string description: Nome canonico del Tipo di Entità examples: - Istituti e Luoghi Della Cultura Italiani (musei, biblioteche, cinema, ecc) native: type: boolean description: Se il Tipo è nativo di piattaforma o importato readOnly: true default: false # stateType: # $ref: '#/components/schemas/State' syntax: type: string format: json description: Definizione (JSON-LD) della sintassi del Tipo di Entità examples: - { "@context": "https://json-ld.org/contexts/person.jsonld", "@id": "http://dbpedia.org/resource/John_Lennon", "name": "John Lennon", "born": "1940-10-09", "spouse": "http://dbpedia.org/resource/Cynthia_Lennon" } terminology: $ref: '#/components/schemas/Terminology' examples: - http://dati.beniculturali.it/cis uri: type: string format: uri description: URI autoritativo del Tipo (se non nativo) examples: - http://dati.beniculturali.it/cis/CulturalInstituteOrSite # State: # type: object # description: Definisce una possibile rappresentazione della situazione attuale nel «divenire» delle Entità di un certo Tipo # examples: # - Aperto o Chiuso # - Acceso o Spento # - (StatoSemaforo) Rosso, Giallo, Verde, Lampeggiante, Spento # - TemperaturaAmbiente - la temperatura attuale di un ambiente in gradi centigradi # properties: # id: # type: string # format: uri # description: ID univoco del Tipo di Stato # name: # type: string # description: Nome canonico del Tipo di Stato # uom: # type: string # description: Unità di misura (per grandezze scalari) # kind: # type: string # description: La tipologia elementare del Tipo di Stato (grandezza con unità di misura, stringa, eccetera) # examples: # - Enumeration # - Number # - String Entity: type: object description: rappresenta un generico oggetto urbano, è di uno specifico Tipo, afferisce a una Sorgente Dati, ha uno Stato dinamico, è dotato di proprietà type-specific, può avere un DataPoint associato, è tipicamente geo-localizzabile required: [id, type, source, createdDate, updatedDate] properties: id: type: string format: uri description: ID univoco dell'Entità sulla piattaforma examples: [20738] name: type: string description: Nome canonico dell'Entità sulla piattaforma examples: - Antiquarium e Acquedotto romano di Trieste geometry: type: object description: Coordinate geografiche dell'Entità properties: lat: type: number description: Latitudine dell'Entità examples: [45.61809] long: type: number description: Longitudine dell'Entità examples: [13.827805] type: $ref: '#/components/schemas/Type' parent: $ref: '#/components/schemas/Entity' source: $ref: '#/components/schemas/Source' externalId: type: string description: Identificativo dell'Entità nel sistema sorgente examples: - http://dati.beniculturali.it/mibact/luoghi/resource/CISNameInTime/20738 state: type: object description: Stato dell'entità properties: value: type: string # description: Valore dello stato (determinato da Type.stateType) description: Valore dello stato timestamp: type: string format: date-time description: Data/ora dello stato # validity: # type: object # properties: # from: # type: string # format: date-time # description: Inizio validità # to: # type: string # format: date-time # description: Fine validità payload: type: object description: Attributi personalizzati in base al tipo di entità additionalProperties: true examples: - { chiusura: 'Lunedì|Giovedì|Domenica' } dataPoint: description: DataPoint associato all'entità $ref: '#/components/schemas/DataPoint' createdDate: type: string format: date-time readOnly: true description: Data e ora di creazione dell'entità (timestamp ISO 8601) updatedDate: type: string format: date-time readOnly: true description: Data e ora dell'ultima modifica all'entità, escluse le modifiche di stato (timestamp ISO 8601) Source: type: object description: Fonte dati, interna o esterna, relativa a un soggetto alimentante properties: id: type: string format: uri description: ID univoco della Fonte Dati examples: - 'fvg_ispfor_tsgo' - 'fvg_ispfor' name: type: string description: Nome canonico della Fonte Dati examples: - 'Ministero per i Beni e le Attività Culturali' - 'Vincolo idrogeologico. L. 3267/1923 Comune di Trieste' - 'Ispettorati forestali' - 'Recupero energetico di biogas da digestione anaerobica o da discarica R1 (BDAD)' - 'Area golenale' - 'Copertura 2019 della banda larga in Italia secondo i criteri di rilevazione DESI 2020' internal: type: boolean description: Indica se la fonte dati è nativa della piattaforma o meno readOnly: true default: false organization: type: string description: Organizzazione di riferimento (ovvero soggetto alimentante) per la Fonte Dati examples: - 'Ministero per i Beni e le Attività Culturali' - 'Regione Autonoma Friuli Venezia Giulia - ISPETTORATO FORESTALE DI TRIESTE E GORIZIA' - 'RAFVG - DC Risorse agroalimentari, forestali e ittiche - Area foreste e territorio' - 'Regione Autonoma Friuli Venezia Giulia - SERVIZIO DISCIPLINA GESTIONE RIFIUTI E SITI INQUINATI' - 'Regione Autonoma Friuli Venezia Giulia - SERVIZIO GEOLOGICO' - 'Autorità per le Garanzie nelle Comunicazioni - AGCOM' processor: type: string description: Organizzazione che gestisce tecnicamente la Fonte Dati examples: - 'Insiel S.p.A.' - 'Regione autonoma Friuli Venezia Giulia' required: [id, name, organization, internal] DataPoint: type: object description: Dispositivo IoT installato su un Data Point gestito nativamente in piattaforma required: [id, fk_firmware_id, fk_tenant_code, fk_device_service_id, created_date, updated_date] properties: id: type: string format: uri description: Identificativo univoco del data point serial: type: string description: Seriale del dispositivo installato sul data point fk_tenant_code: type: string format: uri description: Identificativo univoco del tenant appartenente il dispositivo fk_service_id: type: string format: uri description: Identificativo univoco del servizio gps_latitude: type: number format: double minimum: -90 maximum: 90 description: coordinate gps della latitudine gps_longitude: type: number format: double minimum: -90 maximum: 90 description: coordinate gps della logitudine street: type: string description: via del data point street_number: type: string description: numero civico del data point city: type: string description: citta del data point postal_code: type: string description: cap del data point createdDate: type: string format: date-time description: Data di creazione updatedDate: type: string format: date-time description: Ultimo aggiornamento Measure: type: object properties: id: type: integer format: int64 description: Identificazione univoca della misura data_point: type: string description: Data point dove è installato il dispositivo serial: type: string description: Seriale del dispositivo #deviceId: # type: integer # format: int64 # description: Foreign key to the related device # description: Device associato all'entità # $ref: '#/components/schemas/Device' measure_date: type: string format: date-time description: Data della misura measure_name: type: string description: Nome della misura unit_of_measurement: type: string description: Unità di misura della misura (e.g., °C, %, V) diagnostic: type: string description: Bitmask di diagnostica se disponibile type: type: string description: Tipo di misura status: type: string description: Stato corrente della misura battery_percentage: type: integer minimum: 0 maximum: 100 description: Livello batteria in percentuale receipt_date: type: string format: date-time description: Data ricezione della misura created_date: type: string format: date-time description: Timestamp di creazione del record updated_date: type: string format: date-time description: Timestamp di ultimo aggiornamento del record payload: description: Payload della misura $ref: '#/components/schemas/Payload' required: - id - serial - data_point - measure_date - measure_name - measure_value - unit_of_measurement MeasurementType: type: object description: Tipi di misure, comprensivi di riferimento al nomenclatore e definizione della struttura del payload specifico required: [id, name, syntax] properties: id: type: string format: uri description: Identificativo univoco del Tipo di Misura name: type: string description: Nome canonico del Tipo di Misura syntax: type: string format: json description: Definizione (JSON-LD) della sintassi del Tipo di Misura examples: - https://github.com/FIWARE/data-models/tree/master/specs/PointOfInterest Payload: type: object description: Payload della misura properties: type: $ref: '#/components/schemas/MeasurementType' value: type: object additionalProperties: true securitySchemes: panorama_auth: type: oauth2 flows: implicit: authorizationUrl: https://panorama.edisonnext.it/oauth/authorize scopes: "write:entities": Panorama data provider "read:entities": Panorama data consumer "write:types": Panorama tenant administrator panorama_consumer_api_key: type: apiKey name: consumerApiKey in: header panorama_provider_api_key: type: apiKey name: providerApiKey in: header panorama_administrator_api_key: type: apiKey name: administratorApiKey in: header