Google Cloud IoT Core verrà ritirato il 16 agosto 2023. Per saperne di più, contatta il team dedicato al tuo account Google Cloud.

Acquisizione dello stato dei dispositivi

Mantieni tutto organizzato con le raccolte Salva e classifica i contenuti in base alle tue preferenze.

Con Cloud IoT Core puoi monitorare lo stato di ciascun dispositivo connesso. Lo stato viene segnalato dal dispositivo come dati binari. Gli aggiornamenti dello stato del dispositivo sono generalmente attivati da una modifica del dispositivo, che può essere un aggiornamento della configurazione da Cloud IoT Core o una modifica simile eseguita da un'altra sorgente esterna, ad esempio un aggiornamento del firmware.

Lo stato del dispositivo è diverso dalla configurazione del dispositivo. I dati di configurazione vengono inviati al dispositivo da Cloud IoT Core. I dati sullo stato vengono inviati dal dispositivo a Cloud IoT Core. Puoi considerare la configurazione come un'istruzione esterna e lo stato come una rappresentazione interna.

Cloud IoT Core può aiutarti a rispondere a domande di base sulla configurazione e sullo stato: cosa pensa che dovrebbe fare il dispositivo attualmente? Qual è la differenza con la configurazione più recente del dispositivo?

Limiti

Gli aggiornamenti dello stato sono limitati a 1 aggiornamento al secondo, per dispositivo. Tuttavia, per ottenere risultati ottimali, lo stato del dispositivo dovrebbe essere aggiornato con minore frequenza, al massimo una volta ogni 10 secondi.

La frequenza di aggiornamento viene calcolata come il tempo tra il riconoscimento più recente del server e la successiva richiesta di aggiornamento.

Registrazione dello stato del dispositivo

Bridge MQTT

Per segnalare lo stato a Cloud IoT Core tramite il bridge MQTT, pubblica i messaggi nell'argomento MQTT /devices/DEVICE_ID/state. Puoi selezionare un argomento Cloud Pub/Sub per archiviare gli eventi di stato quando crei o aggiorni un registro.

Per ulteriori dettagli, consulta Pubblicazione tramite il bridge MQTT.

Bridge HTTP

Per segnalare lo stato a Cloud IoT Core tramite il bridge HTTP, i dispositivi devono utilizzare una richiesta setState. I dati dello stato binario vengono passati nel corpo della richiesta come stringa con codifica base64.

Per maggiori dettagli, consulta Pubblicazione tramite il bridge HTTP.

Recupero dati sullo stato del dispositivo

Questa sezione spiega come ottenere i dati di stato segnalati a Cloud IoT Core dai dispositivi. I dispositivi non possono leggere i dati di stato nel cloud.

I dati sullo stato vengono restituiti in formato binario. I dati sullo stato potrebbero avere una struttura diversa da quella dei dati di configurazione che attivano la modifica dello stato.

Ad esempio, supponiamo che tu abbia un dispositivo con diversi fan. I dati di configurazione potrebbero essere un oggetto JSON contenente un semplice valore booleano che abilita o disabilita il raffreddamento:

Esempio di dati di configurazione

{
  'cooling': true
}

Tuttavia, i dati sullo stato del dispositivo potrebbero includere informazioni di diagnostica e i dati della ventola che dovresti vedere in risposta a una modifica di 'cooling':

Esempio di dati sullo stato

{
  'fan1_target_rpm': 1000,
  'fan2_target_rpm': 1200,
  'firmware_version': '1.2.3b'
}

Il firmware_version del dispositivo non è correlato ai dati di configurazione, ma restituisce la rappresentazione interna completa del suo stato. Questo esempio illustra in che modo lo stato dei dispositivi può essere utile per il debug in generale, nonché per verificare che i dispositivi abbiano confermato configurazioni specifiche.

Puoi ottenere i dati sullo stato del dispositivo utilizzando un argomento Cloud Pub/Sub, la console di Cloud Platform, l'API Cloud IoT Core o gcloud.

Argomento Cloud Pub/Sub

Cloud IoT Core conserva i dati di stato in archiviazione. Puoi anche configurare un argomento Cloud Pub/Sub facoltativo per la notifica dello stato in ogni registro dei dispositivi, tramite Cloud Console, gcloud o l'API. Questo argomento può essere uguale o diverso dall'argomento evento di telemetria.

I dati sullo stato vengono pubblicati in Cloud Pub/Sub nel modo migliore possibile: se la pubblicazione nell'argomento ha esito negativo, non verrà ritentata. Se non viene definito alcun argomento, gli aggiornamenti dello stato del dispositivo vengono mantenuti in modo interno da Cloud IoT Core, ma solo gli ultimi 10 stati vengono conservati.

Console

  1. Vai alla pagina Registry nella console Google Cloud.

    Vai alla pagina Registry

  2. Fai clic sull'ID del registro relativo al dispositivo.

  3. Nel menu del Registro di sistema a sinistra, fai clic su Dispositivi.

  4. Fai clic sull'ID del dispositivo per andare alla pagina Dettagli dispositivo.

  5. Fai clic su Configurazione e cronologia dello stato. Utilizza le caselle di controllo per visualizzare la cronologia delle configurazioni, la cronologia degli stati o entrambe. Per impostazione predefinita, vengono mostrati entrambi.

    • Un segno di spunta verde indica che il dispositivo ha confermato la configurazione (solo MQTT).
    • Un simbolo di avviso giallo indica che il dispositivo non ha ancora confermato la configurazione (solo MQTT).
    • Fai clic su una riga per visualizzare la configurazione completa o i dati sullo stato in JSON, nonché il timestamp e la versione.
  6. Fai clic su Confronta per confrontare i dati di configurazione con i dati di stato. Questa vista può aiutarti a eseguire il debug delle configurazioni e, se utilizzi MQTT, assicurati che i dispositivi abbiano confermato versioni di configurazione specifiche. Il bridge HTTP non supporta la conferma delle configurazioni.

gcloud

Per ricevere i messaggi di stato più recenti per un dispositivo (fino a 10), esegui il comando gcloud iot devices states list.

gcloud iot devices states list \
    --registry=REGISTRY_ID \
    --device=DEVICE_ID \
    --region=REGION

Un flag Cloud Pub/Sub (--state-pubsub-topic) di notifica è disponibile per i comandi gcloud iot registries create e update:

gcloud iot registries create REGISTRY_ID \
    --project=PROJECT_ID \
    --region=REGION \
    [--event-notification-config=topic=TOPIC,[subfolder=SUBFOLDER] [--event-notification-config=...]]
    [--state-pubsub-topic=STATE_PUBSUB_TOPIC]
gcloud iot registries update REGISTRY_ID \
    --project=PROJECT_ID \
    --region=REGION \
    [--event-notification-config=topic=TOPIC,[subfolder=SUBFOLDER] [--event-notification-config=...]]
    [--state-pubsub-topic=STATE_PUBSUB_TOPIC]

API

Utilizza il metodo states.list del dispositivo per visualizzare gli stati più recenti del dispositivo (fino a 10). Ogni risorsa Device ha un campo DeviceState che contiene lo stato ricevuto più di recente dal dispositivo. La risorsa DeviceRegistry ha un campo StateNotificationConfig che può essere utilizzato per specificare un argomento Cloud Pub/Sub per la notifica dello stato durante la creazione o l'aggiornamento di un registro.

L'esempio seguente mostra come recuperare lo stato di un dispositivo dal registro dispositivi:

C#

public static object GetDeviceStates(string projectId, string cloudRegion, string registryId, string deviceId)
{
    var cloudIot = CreateAuthorizedClient();

    // The resource name of the location associated with the key rings.
    var name = $"projects/{projectId}/locations/{cloudRegion}/registries/{registryId}/devices/{deviceId}";

    try
    {
        Console.WriteLine("States: ");
        var res = cloudIot.Projects.Locations.Registries.Devices.States.List(name).Execute();
        res.DeviceStates.ToList().ForEach(state =>
        {
            Console.WriteLine($"\t{state.UpdateTime}: {state.BinaryData}");
        });
    }
    catch (Google.GoogleApiException e)
    {
        Console.WriteLine(e.Message);
        if (e.Error != null) return e.Error.Code;
        return -1;
    }
    return 0;
}

Go


// getDeviceStates retrieves and lists device states.
func getDeviceStates(w io.Writer, projectID string, region string, registryID string, device string) ([]*cloudiot.DeviceState, error) {
	// Authorize the client using Application Default Credentials.
	// See https://g.co/dv/identity/protocols/application-default-credentials
	ctx := context.Background()
	httpClient, err := google.DefaultClient(ctx, cloudiot.CloudPlatformScope)
	if err != nil {
		return nil, err
	}
	client, err := cloudiot.New(httpClient)
	if err != nil {
		return nil, err
	}

	path := fmt.Sprintf("projects/%s/locations/%s/registries/%s/devices/%s", projectID, region, registryID, device)
	response, err := client.Projects.Locations.Registries.Devices.States.List(path).Do()
	if err != nil {
		return nil, err
	}

	fmt.Fprintln(w, "Successfully retrieved device states!")

	for _, state := range response.DeviceStates {
		fmt.Fprintf(w, "%s : %s\n", state.UpdateTime, state.BinaryData)
	}

	return response.DeviceStates, nil
}

Java

/** Retrieves device metadata from a registry. * */
protected static List<DeviceState> getDeviceStates(
    String deviceId, String projectId, String cloudRegion, String registryName)
    throws GeneralSecurityException, IOException {
  GoogleCredentials credential =
      GoogleCredentials.getApplicationDefault().createScoped(CloudIotScopes.all());
  JsonFactory jsonFactory = JacksonFactory.getDefaultInstance();
  HttpRequestInitializer init = new HttpCredentialsAdapter(credential);
  final CloudIot service =
      new CloudIot.Builder(GoogleNetHttpTransport.newTrustedTransport(), jsonFactory, init)
          .setApplicationName(APP_NAME)
          .build();

  final String devicePath =
      String.format(
          "projects/%s/locations/%s/registries/%s/devices/%s",
          projectId, cloudRegion, registryName, deviceId);

  System.out.println("Retrieving device states " + devicePath);

  ListDeviceStatesResponse resp =
      service.projects().locations().registries().devices().states().list(devicePath).execute();

  return resp.getDeviceStates();
}

Node.js

// const cloudRegion = 'us-central1';
// const deviceId = 'my-device';
// const projectId = 'adjective-noun-123';
// const registryId = 'my-registry';
const iot = require('@google-cloud/iot');
const iotClient = new iot.v1.DeviceManagerClient({
  // optional auth parameters.
});

async function listDeviceStates() {
  const devicePath = iotClient.devicePath(
    projectId,
    cloudRegion,
    registryId,
    deviceId
  );

  const [response] = await iotClient.listDeviceStates({name: devicePath});
  const states = response.deviceStates;
  if (states.length === 0) {
    console.log(`No States for device: ${deviceId}`);
  } else {
    console.log(`States for device: ${deviceId}`);
  }

  for (let i = 0; i < states.length; i++) {
    const state = states[i];
    console.log(
      'State:',
      state,
      '\nData:\n',
      state.binaryData.toString('utf8')
    );
  }
}

listDeviceStates();

PHP

use Google\Cloud\Iot\V1\DeviceManagerClient;

/**
 * Retrieve a device's state blobs.
 *
 * @param string $registryId IOT Device Registry ID
 * @param string $deviceId IOT Device ID
 * @param string $projectId Google Cloud project ID
 * @param string $location (Optional) Google Cloud region
 */
function get_device_state(
    $registryId,
    $deviceId,
    $projectId,
    $location = 'us-central1'
) {
    print('Getting device state' . PHP_EOL);

    // Instantiate a client.
    $deviceManager = new DeviceManagerClient();
    $deviceName = $deviceManager->deviceName($projectId, $location, $registryId, $deviceId);

    $response = $deviceManager->listDeviceStates($deviceName);

    foreach ($response->getDeviceStates() as $state) {
        print('State:' . PHP_EOL);
        printf('    Data: %s' . PHP_EOL, $state->getBinaryData());
        printf('    Update Time: %s' . PHP_EOL,
            $state->getUpdateTime()->toDateTime()->format('Y-m-d H:i:s'));
    }
}

Python

Questo esempio utilizza la libreria client delle API di Google per Python.
# project_id = 'YOUR_PROJECT_ID'
# cloud_region = 'us-central1'
# registry_id = 'your-registry-id'
# device_id = 'your-device-id'
client = iot_v1.DeviceManagerClient()
device_path = client.device_path(project_id, cloud_region, registry_id, device_id)

device = client.get_device(request={"name": device_path})
print("Last state: {}".format(device.state))

print("State history")
states = client.list_device_states(request={"name": device_path}).device_states
for state in states:
    print("State: {}".format(state))

return states

Ruby

# project_id  = "Your Google Cloud project ID"
# location_id = "The Cloud region the registry is located in"
# registry_id = "The registry to get device states from"
# device_id   = "The identifier of the device to get states for"

require "google/apis/cloudiot_v1"

# Initialize the client and authenticate with the specified scope
Cloudiot   = Google::Apis::CloudiotV1
iot_client = Cloudiot::CloudIotService.new
iot_client.authorization = Google::Auth.get_application_default(
  "https://www.googleapis.com/auth/cloud-platform"
)

# The resource name of the location associated with the project
parent   = "projects/#{project_id}/locations/#{location_id}"
resource = "#{parent}/registries/#{registry_id}/devices/#{device_id}"

# List the configurations for the provided device
result = iot_client.list_project_location_registry_device_states(
  resource
)
if result.device_states
  result.device_states.each do |state|
    puts "#{state.update_time}: #{state.binary_data}"
  end
else
  puts "No state messages"
end