community italiana di domotica personale
 
Le API Shelly di seconda generazione: una panoramica tecnica

Le API Shelly di seconda generazione: una panoramica tecnica

Amazon - Promozioni del giorno
NOTA IMPORTANTE: l’articolo che segue prevede una certa preparazione tecnica. Chi non la possedesse tenga presente la reale possibilità di non comprendere certi concetti – che comunque possono essere chiariti facendosi una cultura anche usufruendo del nostro forum e della chat Telegram.

Shelly Logo

Come abbiamo accennato anche nella recensione del primo prodotto di seconda generazione che abbiamo testato, lo Shelly 1 Plus, il produttore Allterco ha completamente rivisto per questo nuovo corso la parte legata all’interoperabilità, migrando all’utilizzo del protocollo RPC (più precisamente, JSON-RPC 2.0). Si tratta di un protocollo client-server (request-response) sincrono.

Shelly 1 Plus

Questo, come vedremo, ha concesso ad Allterco di standardizzare le interfacce e rendere il tutto molto più strutturato. In precedenza, con i device di prima generazione, potevamo controllare o recuperare informazioni dal device in maniera diversa a seconda del protocollo che volevamo utilizzare; ora invece, indipendentemente dalla modalità di comunicazione scelta tra quelle messe a disposizione potremo fare sempre le stesse identiche cose.

Secondo quanto previsto dall’implementazione di questo protocollo, ogni “azione” che effettuiamo – sia essa per monitorare che per controllare un device – corrisponde ad un “metodo” che prevede in input un oggetto in notazione JSON e che restituisce, quando evocato, un altro oggetto JSON quale risultato. Questi metodi sono raggruppati per “namespace”. Per fare un esempio, il namespace “Switch” che riguarderà appunto gli switch, accorperà n metodi per l’interazione, come ad esempio quello per recuperare la configurazione “Getconfig”, quello per impostare uno stato “Set”, eccetera.

Esempio:

Switch.Getconfig
Switch.Set

Ma come funziona effettivamente la comunicazione tra il client (l’utente) ed il device ? La comunicazione avviene tramite l’invio/ricezione dei tre cosiddetti “frame”, che sono sostanzialmente degli oggetti JSON:

  • request frame
  • response frame
  • notification frame

Prendendo come spunto il namespace “Switch” appena menzionato, ammettiamo di voler impartire un comando per far cambiare stato allo switch esposto su uno Shelly. Dividiamo per frame ed in modo sequenziale le operazioni:

REQUEST FRAME

Il client (nel nostro caso l’utente/il nostro hub) invierà il request frame composto dai seguenti attributi:

  • id (obbligatorio): identificativo della request. E’ obbligatorio se si vuole ricevere il response frame;
  • src (obbligatorio): identificativo di chi ha inviato la request (nel nostro caso abbiamo impostato la stringa “homeassistant” ipotizzando di integrare lo Shelly sul noto HUB personale);
  • method (obbligatorio): è una stringa che rappresenta il metodo da invocare;
  • params (opzionale): è un oggetto JSON con i parametri eventualmente previsti dal metodo invocato.

Ecco un esempio di request frame:

{
   "id":1,
   "src":"homeassistant",
   "method":"Switch.Set",
   "params":{
      "id":0,
      "on":true
   }
}

RESPONSE FRAME

Il server (nel nostro caso lo Shelly), se indicato tramite l’id del request frame, invierà in risposta il response frame che sarà composto dai seguenti attributi:

  • id: identificativo corrispondente a quello della request;
  • src: identificativo di chi ha inviato il frame (nel nostro caso lo Shelly);
  • dst: identificativo del destinatario del response frame che corrisponderà al “src” presente nel request frame;
  • result: è un oggetto JSON con i parametri restituiti dal server.

Ecco un esempio di response frame:

{
   "id":1,
   "src":"shellyplus1-a8032abdcb2c",
   "dst":"homeassistant",
   "result":{
      "was_on":false
   }
}

Se ci fosse stato un errore, al posto di result avremmo avuto error. Di seguito un esempio:

{
   "id":1,
   "src":"shellyplus1-a8032abdcb2c",
   "dst": "homeassistant",
   "error": {
      "code": -105,
      "message": "Bad id=12"
   }
}

NOTIFICATION FRAME

Ultimo step. Il server (sempre lo Shelly) invierà il notification frame al cui interno ci saranno le informazioni relative ad un cambio stato: si precisa questo perché nel caso in cui inviassimo un request frame per passare in stato “on” quando lo switch è già in stato “on”, non verrebbe inviato alcun notification frame.

Il notification frame ad ogni modo è molto simile ad un request frame, ma in questo caso ovviamente il giro è chiuso e non si aspetta a sua volta un response frame.

È composto dai seguenti attributi:

  • src: l’identificativo di chi invia il response frame;
  • dst: l’identificativo del destinatario del notification frame;
  • method: il metodo invocato (che è in questo caso è NotifyStatus);
  • params: è un JSON object contenente i parametri relativi alla telemetria:
{
   "src":"shellyplus1-a8032abdcb2c",
   "dst":"shellyplus1-a8032abdcb2c/events",
   "method":"NotifyStatus",
   "params":{
      "ts":1633816032.14,
      "switch:0":{
         "id":0,
         "output":true,
         "source":"MQTT"
      }
   }

Piccola nota sull’attributo dst, il quale potrebbe confondere le idee. Immaginiamo che ci si possa aspettare “dst”:”homeassistant”. Come ragionamento è corretto, ma in questo caso, per questo esempio, come è possibile notare anche dall’ultimo JSON di notifica, il test è stato effettuato via MQTT ed in questo caso l’identificativo del destinatario non è “homeassistant” da cui è partita la prima publish, ma il topic apposito per i frame di notifica “shellydevicemodel-XXXXXXXXXXXX/events/rpc“, ecco perché troviamo “shellyplus1-a8032abdcb2c/events“.

Se avessimo fatto una prova utilizzando ad esempio websocket (usando wscat) il dst nel notification frame sarebbe stato effettivamente diverso:

$ wscat -c ws://http://192.168.1.8/rpc
Connected (press CTRL+C to quit)
> {"id":2, "src":"homeassistant", "method":"Switch.Set", "params":{"id":0, "on":true}}
< {"id":2,"src":"shellyplus1-a8032abdcb2c","dst":"homeassistant","result":{"was_on":false}}
< {"src":"shellyplus1-a8032abdcb2c","dst":"homeassistant","method":"NotifyStatus","params":{"ts":1633817170.00,"switch:0":{"id":0,"output":true,"source":"WS_in"}}}

Proprio da questo ultimo aspetto, come accennato anche all’inizio, possiamo notare come effettivamente sia possiible fare le stesse cose ma con strumenti e protocolli completamente diversi, anche detti RPC Channels. Nel momento in cui stiamo scrivendo questo articolo quelli supportati sono:

  • HTTP
  • Websocket
  • MQTT
  • UDP

Tutto ciò che possiamo fare è possibile farlo grazie ai metodi che abbiamo accennato essere raggruppati per namespace.
Questi namespace a loro volta li possiamo dividere a livello logico in n categorie.

Tenendo sempre in considerazione che la lista dei namespace e dei metodi è in continua evoluzione lato Shelly, per darvi un’idea di ciò che è possibile fare, è possibile fare un salto sul sito di documentazione ufficiale per censirli tutti.

Alcuni namespace sono:

  • Shelly: controllo del device (es. recupero configurazioni, aggiornamento firmware, Reboot, etc.);
  • Schedule: gestione temporizzazioni lato device;
  • Webhook: gestione webhook sul device;
  • HTTP: gestione request HTTP/S in GET e POST dal device.

Esiste poi la categoria “Components” che a sua volta si suddivide nelle seguenti sottocategorie:

  • System components:
    • System: permette di recuperare gli attributi a livello di sistema come uptime, ram, mac address, disponibilità aggiornamenti, eccetera;
    • Ethernet: restituisce i parametri relativi alla connessione via cavo come ad esempio ip, netmask, gw);
    • WiFi: come il precedente, ma relativa ovviamente al Wi-Fi restituendo anche parametri quali SSID, RSSI, stato, IP, eccetera;
    • BLE: restituisce solo lo stato del bluetooth (attivo/non attivo);
    • Cloud: come per il precedente, ma ovviamente riferito allo stato della connettività verso il cloud Shelly;
    • MQTT: restituisce lo stato della connettività verso il broker MQTT.
  • Functional components:
    • Input: controllo e configurazione degli input collegati allo Shelly;
    • Switch: controllo e configurazione del relè;
  • Notifications: i metodi delle notifiche di eventi di cambio stato e non. Non verranno mai utilizzati lato client in quanto si tratta dei metodi utilizzati per l’invio delle notifiche da parte del device;
  • Script: permette di controllare gli script (creare, cancellare, avviare, interrompere), una delle grosse novità dei device di seconda generazione.


Questa pagina è redatta, manutenuta e aggiornata dallo staff di inDomus, un gruppo di persone molto diverse tra loro che trovi, per domande e supporto, sul forum e sulla chat del sito. Se ti sei perso, a tua disposizione c'è la mappa.
Amazon - Promozioni del giorno