Carregue ficheiros do seu dispositivo para a nuvem com o Hub IoT do Azure (Java)

Este artigo demonstra como carregar um arquivo do Hub IoT para carregar um arquivo no armazenamento de blobs do Azure, usando Java.

Os artigos Enviar telemetria de um dispositivo para um início rápido do hub IoT e Enviar mensagens da nuvem para o dispositivo com o Hub IoT mostram a funcionalidade básica de mensagens de dispositivo para nuvem e de nuvem para dispositivo do Hub IoT. O tutorial Configurar roteamento de mensagens com o Hub IoT mostra uma maneira confiável de armazenar mensagens do dispositivo para a nuvem no armazenamento de blobs do Azure. No entanto, em alguns cenários, você não pode mapear facilmente os dados que seus dispositivos enviam para as mensagens relativamente pequenas de dispositivo para nuvem que o Hub IoT aceita. Por exemplo:

  • Vídeos
  • Arquivos grandes que contêm imagens
  • Dados de vibração amostrados em alta frequência
  • Alguma forma de dados pré-processados.

Esses arquivos geralmente são processados em lote na nuvem, usando ferramentas como o Azure Data Factory ou a pilha Hadoop . Quando você precisa carregar arquivos de um dispositivo, ainda pode usar a segurança e a confiabilidade do Hub IoT. Este artigo mostra-lhe como. Veja dois exemplos de azure-iot-sdk-java no GitHub.

Nota

O Hub IoT dá suporte a muitas plataformas e linguagens de dispositivo (incluindo C, .NET e JavaScript) por meio de SDKs de dispositivo IoT do Azure. Consulte o Azure IoT Developer Center para saber como conectar seu dispositivo ao Hub IoT do Azure.

Importante

A funcionalidade de carregamento de ficheiros em dispositivos que utilizam a autenticação da autoridade de certificação (CA) X.509 está em pré-visualização pública e o modo de pré-visualização tem de estar ativado. Está geralmente disponível em dispositivos que utilizam a autenticação de impressão digital X.509 ou o atestado de certificado X.509 com o Serviço de Aprovisionamento de Dispositivos do Azure. Para saber mais sobre a autenticação X.509 com o Hub IoT, consulte Certificados X.509 suportados.

Pré-requisitos

  • Um hub IoT. Crie um com a CLI ou o portal do Azure.

  • Um dispositivo registado. Registre um no portal do Azure.

  • Kit de Desenvolvimento Java SE 8. Certifique-se de selecionar Java 8 em Suporte de longo prazo para obter downloads para JDK 8.

  • Maven 3

  • A porta 8883 deve estar aberta no firewall. O exemplo de dispositivo neste artigo usa o protocolo MQTT, que se comunica pela porta 8883. Essa porta pode estar bloqueada em alguns ambientes de rede corporativa e educacional. Para obter mais informações e maneiras de contornar esse problema, consulte Conectando-se ao Hub IoT (MQTT).

Associar uma conta de Armazenamento do Azure ao Hub IoT

Para carregar arquivos de um dispositivo, você deve ter uma conta de Armazenamento do Azure e um contêiner de Armazenamento de Blob do Azure associados ao seu hub IoT. Depois de associar a conta de armazenamento e o contêiner ao hub IoT, o hub IoT pode fornecer os elementos de um URI SAS quando solicitado por um dispositivo. O dispositivo pode usar esses elementos para construir o URI SAS que ele usa para autenticar com o Armazenamento do Azure e carregar arquivos no contêiner de blob.

Para associar uma conta de Armazenamento do Azure ao seu hub IoT:

  1. Em Configurações do Hub, selecione Carregamento de arquivo no painel esquerdo do seu hub IoT.

    Captura de tela mostrando as configurações de upload de arquivos selecionados do portal.

  2. No painel Carregamento de arquivo, selecione Contêiner de Armazenamento do Azure. Para este artigo, é recomendável que sua conta de armazenamento e o Hub IoT estejam localizados na mesma região.

    • Se você já tiver uma conta de armazenamento que deseja usar, selecione-a na lista.

    • Para criar uma nova conta de armazenamento, selecione +Conta de armazenamento. Forneça um nome para a conta de armazenamento e verifique se o Local está definido para a mesma região do seu hub IoT e, em seguida, selecione OK. A nova conta é criada no mesmo grupo de recursos do seu hub IoT. Quando a implantação for concluída, selecione a conta de armazenamento na lista.

    Depois de selecionar a conta de armazenamento, o painel Contêineres é aberto.

  3. No painel Contêineres, selecione o contêiner de blob.

    • Se você já tiver um contêiner de blob que deseja usar, selecione-o na lista e clique em Selecionar.

    • Para criar um novo contêiner de blob, selecione + Contêiner. Forneça um nome para o novo contêiner. Para os fins deste artigo, você pode deixar todos os outros campos em seu padrão. Selecione Criar. Quando a implantação for concluída, selecione o contêiner na lista e clique em Selecionar.

  4. De volta ao painel Carregamento de ficheiros, certifique-se de que as notificações de ficheiros estão definidas como Ativado. Você pode deixar todas as outras configurações em seus padrões. Selecione Salvar e aguarde a conclusão das configurações antes de passar para a próxima seção.

    Captura de tela mostrando as configurações de confirmação de upload de arquivos no portal.

Para obter instruções mais detalhadas sobre como criar uma conta de Armazenamento do Azure, consulte Criar uma conta de armazenamento. Para obter instruções mais detalhadas sobre como associar uma conta de armazenamento e um contêiner de blob a um hub IoT, consulte Configurar carregamentos de arquivos usando o portal do Azure.

Criar um projeto usando o Maven

Crie um diretório para seu projeto e inicie um shell nesse diretório. Na linha de comando, execute o seguinte

mvn archetype:generate -DgroupId=com.mycompany.app -DartifactId=my-app -DarchetypeArtifactId=maven-archetype-quickstart -DarchetypeVersion=1.4 -DinteractiveMode=false

Isso gera um diretório com o mesmo nome que o artifactId e uma estrutura de projeto padrão:

  my-app
  |-- pom.xml
   -- src
      -- main
         -- java
            -- com
               -- mycompany
                  -- app
                     --App.Java

Usando um editor de texto, substitua o arquivo pom.xml pelo seguinte:


<?xml version="1.0" encoding="UTF-8"?>

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
  <modelVersion>4.0.0</modelVersion>

  <groupId>com.mycompany.app</groupId>
  <artifactId>my-app</artifactId>
  <version>1.0-SNAPSHOT</version>

  <name>my-app</name>
  <!-- FIXME change it to the project's website -->
  <url>http://www.example.com</url>

  <properties>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    <maven.compiler.source>1.7</maven.compiler.source>
    <maven.compiler.target>1.7</maven.compiler.target>
  </properties>

  <dependencies>
      <dependency>
      <groupId>com.microsoft.azure.sdk.iot</groupId>
      <artifactId>iot-device-client</artifactId>
      <version>1.30.1</version>
    </dependency>
    <dependency>
      <groupId>org.slf4j</groupId>
      <artifactId>slf4j-log4j12</artifactId>
      <version>1.7.29</version>
    </dependency>    
    <dependency>
      <groupId>junit</groupId>
      <artifactId>junit</artifactId>
      <version>4.11</version>
      <scope>test</scope>
    </dependency>
  </dependencies>

  <build>
    <pluginManagement><!-- lock down plugins versions to avoid using Maven defaults (may be moved to parent pom) -->
      <plugins>
        <plugin>
          <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-compiler-plugin</artifactId>
            <version>3.3</version>
            <configuration>
              <source>1.7</source>
              <target>1.7</target>
            </configuration>
        </plugin>
        <plugin>
          <artifactId>maven-shade-plugin</artifactId>
          <version>2.4</version>
          <executions>
              <execution>
                  <phase>package</phase>
                  <goals>
                    <goal>shade</goal>
                  </goals>
                  <configuration>
                      <filters>
                          <filter>
                              <artifact>*:*</artifact>
                              <excludes>
                                  <exclude>META-INF/*.SF</exclude>
                                  <exclude>META-INF/*.RSA</exclude>
                              </excludes>
                          </filter>
                      </filters>
                      <shadedArtifactAttached>true</shadedArtifactAttached>
                      <shadedClassifierName>with-deps</shadedClassifierName>
                  </configuration>
              </execution>
          </executions>
        </plugin>
      </plugins>
    </pluginManagement>
  </build>
</project>

Carregar um ficheiro a partir de uma aplicação de dispositivo

Copie o arquivo que você deseja carregar para a pasta na árvore do my-app projeto. Usando um editor de texto, substitua App.java pelo código a seguir. Forneça a cadeia de conexão do dispositivo e o nome do arquivo onde indicado. Você copiou a cadeia de conexão do dispositivo quando registrou o dispositivo.

package com.mycompany.app;

import com.azure.storage.blob.BlobClient;
import com.azure.storage.blob.BlobClientBuilder;
import com.microsoft.azure.sdk.iot.deps.serializer.FileUploadCompletionNotification;
import com.microsoft.azure.sdk.iot.deps.serializer.FileUploadSasUriRequest;
import com.microsoft.azure.sdk.iot.deps.serializer.FileUploadSasUriResponse;
import com.microsoft.azure.sdk.iot.device.DeviceClient;
import com.microsoft.azure.sdk.iot.device.IotHubClientProtocol;

import java.io.BufferedInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.net.URISyntaxException;
import java.util.Scanner;

public class App 
{
    /**
     * Upload a single file to blobs using IoT Hub.
     *
     */
    public static void main(String[] args)throws IOException, URISyntaxException
    {
        String connString = "Your device connection string here";
        String fullFileName = "Path of the file to upload";

        System.out.println("Starting...");
        System.out.println("Beginning setup.");

        // File upload will always use HTTPS, DeviceClient will use this protocol only
        //   for the other services like Telemetry, Device Method and Device Twin.
        IotHubClientProtocol protocol = IotHubClientProtocol.MQTT;

        System.out.println("Successfully read input parameters.");

        DeviceClient client = new DeviceClient(connString, protocol);

        System.out.println("Successfully created an IoT Hub client.");

        try
        {
            File file = new File(fullFileName);
            if (file.isDirectory())
            {
                throw new IllegalArgumentException(fullFileName + " is a directory, please provide a single file name, or use the FileUploadSample to upload directories.");
            }

            System.out.println("Retrieving SAS URI from IoT Hub...");
            FileUploadSasUriResponse sasUriResponse = client.getFileUploadSasUri(new FileUploadSasUriRequest(file.getName()));

            System.out.println("Successfully got SAS URI from IoT Hub");
            System.out.println("Correlation Id: " + sasUriResponse.getCorrelationId());
            System.out.println("Container name: " + sasUriResponse.getContainerName());
            System.out.println("Blob name: " + sasUriResponse.getBlobName());
            System.out.println("Blob Uri: " + sasUriResponse.getBlobUri());

            System.out.println("Using the Azure Storage SDK to upload file to Azure Storage...");

            try
            {
                BlobClient blobClient =
                    new BlobClientBuilder()
                        .endpoint(sasUriResponse.getBlobUri().toString())
                        .buildClient();

                blobClient.uploadFromFile(fullFileName);
            }
            catch (Exception e)
            {
                System.out.println("Exception encountered while uploading file to blob: " + e.getMessage());

                System.out.println("Failed to upload file to Azure Storage.");

                System.out.println("Notifying IoT Hub that the SAS URI can be freed and that the file upload failed.");

                // Note that this is done even when the file upload fails. IoT Hub has a fixed number of SAS URIs allowed active
                // at any given time. Once you are done with the file upload, you should free your SAS URI so that other
                // SAS URIs can be generated. If a SAS URI is not freed through this API, then it will free itself eventually
                // based on how long SAS URIs are configured to live on your IoT Hub.
                FileUploadCompletionNotification completionNotification = new FileUploadCompletionNotification(sasUriResponse.getCorrelationId(), false);
                client.completeFileUpload(completionNotification);

                System.out.println("Notified IoT Hub that the SAS URI can be freed and that the file upload was a failure.");

                client.closeNow();
                return;
            }

            System.out.println("Successfully uploaded file to Azure Storage.");

            System.out.println("Notifying IoT Hub that the SAS URI can be freed and that the file upload was a success.");
            FileUploadCompletionNotification completionNotification = new FileUploadCompletionNotification(sasUriResponse.getCorrelationId(), true);
            client.completeFileUpload(completionNotification);
            System.out.println("Successfully notified IoT Hub that the SAS URI can be freed, and that the file upload was a success");
        }
        catch (Exception e)
        {
            System.out.println("On exception, shutting down \n" + " Cause: " + e.getCause() + " \nERROR: " +  e.getMessage());
            System.out.println("Shutting down...");
            client.closeNow();
        }

        System.out.println("Press any key to exit...");

        Scanner scanner = new Scanner(System.in);
        scanner.nextLine();
        System.out.println("Shutting down...");
        client.closeNow();
    }
}

Compilar e executar a aplicação

Em um prompt de my-app comando na pasta, execute o seguinte comando:

mvn clean package -DskipTests

Quando a compilação estiver concluída, execute o seguinte comando para executar o aplicativo:

mvn exec:java -Dexec.mainClass="com.mycompany.app.App"

Você pode usar o portal para exibir o arquivo carregado no contêiner de armazenamento que você configurou:

Captura de ecrã a mostrar um ficheiro que foi carregado para o contentor de armazenamento.

Receber uma notificação de carregamento de ficheiros

Nesta seção, você cria um aplicativo de console Java que recebe mensagens de notificação de carregamento de arquivos do Hub IoT.

  1. Crie um diretório para seu projeto e inicie um shell nesse diretório. Na linha de comando, execute o seguinte

    mvn archetype:generate -DgroupId=com.mycompany.app -DartifactId=my-app -DarchetypeArtifactId=maven-archetype-quickstart -DarchetypeVersion=1.4 -DinteractiveMode=false
    
  2. No prompt de comando, navegue até a nova my-app pasta.

  3. Usando um editor de texto, substitua o pom.xmlmy-app arquivo na pasta pelo seguinte. Adicionar a dependência do cliente de serviço permite que você use o pacote iothub-java-service-client em seu aplicativo para se comunicar com seu serviço de hub IoT:

    <?xml version="1.0" encoding="UTF-8"?>
    
    <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
      xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
      <modelVersion>4.0.0</modelVersion>
    
      <groupId>com.mycompany.app</groupId>
      <artifactId>my-app</artifactId>
      <version>1.0-SNAPSHOT</version>
    
      <name>my-app</name>
      <!-- FIXME change it to the project's website -->
      <url>http://www.example.com</url>
    
      <properties>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
        <maven.compiler.source>1.7</maven.compiler.source>
        <maven.compiler.target>1.7</maven.compiler.target>
      </properties>
    
      <dependencies>
          <dependency>
          <groupId>com.microsoft.azure.sdk.iot</groupId>
          <artifactId>iot-device-client</artifactId>
          <version>1.30.1</version>
        </dependency>
        <dependency>
          <groupId>com.microsoft.azure.sdk.iot</groupId>
          <artifactId>iot-service-client</artifactId>
          <version>1.7.23</version>
        </dependency>
        <dependency>
          <groupId>org.slf4j</groupId>
          <artifactId>slf4j-log4j12</artifactId>
          <version>1.7.29</version>
        </dependency>    
        <dependency>
          <groupId>junit</groupId>
          <artifactId>junit</artifactId>
          <version>4.11</version>
          <scope>test</scope>
        </dependency>
      </dependencies>
    
      <build>
        <pluginManagement><!-- lock down plugins versions to avoid using Maven defaults (may be moved to parent pom) -->
          <plugins>
            <plugin>
              <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-compiler-plugin</artifactId>
                <version>3.3</version>
                <configuration>
                  <source>1.7</source>
                  <target>1.7</target>
                </configuration>
            </plugin>
            <plugin>
              <artifactId>maven-shade-plugin</artifactId>
              <version>2.4</version>
              <executions>
                  <execution>
                      <phase>package</phase>
                      <goals>
                        <goal>shade</goal>
                      </goals>
                      <configuration>
                          <filters>
                              <filter>
                                  <artifact>*:*</artifact>
                                  <excludes>
                                      <exclude>META-INF/*.SF</exclude>
                                      <exclude>META-INF/*.RSA</exclude>
                                  </excludes>
                              </filter>
                          </filters>
                          <shadedArtifactAttached>true</shadedArtifactAttached>
                          <shadedClassifierName>with-deps</shadedClassifierName>
                      </configuration>
                  </execution>
              </executions>
            </plugin>
          </plugins>
        </pluginManagement>
      </build>
    </project>
    

    Nota

    Pode verificar a versão mais recente do iot-service-client utilizando a pesquisa Maven.

  4. Salve e feche o pom.xml arquivo.

  5. Obtenha a cadeia de conexão do serviço Hub IoT.

    Para obter a cadeia de conexão do Hub IoT para a política de serviço , siga estas etapas:

    1. No portal do Azure, selecione Grupos de recursos. Selecione o grupo de recursos onde o hub está localizado e, em seguida, selecione o hub na lista de recursos.

    2. No painel esquerdo do hub IoT, selecione Políticas de acesso compartilhado.

    3. Na lista de políticas, selecione a política de serviço .

    4. Copie a cadeia de conexão primária e salve o valor.

    Captura de tela que mostra como recuperar a cadeia de conexão do seu Hub IoT no portal do Azure.

    Para obter mais informações sobre políticas e permissões de acesso compartilhado do Hub IoT, consulte Controle de acesso e permissões.

  6. Usando um editor de texto, abra o my-app\src\main\java\com\mycompany\app\App.java arquivo e substitua o código pelo seguinte.

    package com.mycompany.app;
    
    import com.microsoft.azure.sdk.iot.service.*;
    import java.io.IOException;
    import java.net.URISyntaxException;
    import java.util.concurrent.ExecutorService;
    import java.util.concurrent.Executors;
    
    
    public class App 
    {
        private static final String connectionString = "{Your service connection string here}";
        private static final IotHubServiceClientProtocol protocol = IotHubServiceClientProtocol.AMQPS;
    
        public static void main(String[] args) throws Exception
        {
            ServiceClient sc = ServiceClient.createFromConnectionString(connectionString, protocol);
    
            FileUploadNotificationReceiver receiver = sc.getFileUploadNotificationReceiver();
            receiver.open();
            FileUploadNotification fileUploadNotification = receiver.receive(2000);
    
            if (fileUploadNotification != null)
            {
                System.out.println("File Upload notification received");
                System.out.println("Device Id : " + fileUploadNotification.getDeviceId());
                System.out.println("Blob Uri: " + fileUploadNotification.getBlobUri());
                System.out.println("Blob Name: " + fileUploadNotification.getBlobName());
                System.out.println("Last Updated : " + fileUploadNotification.getLastUpdatedTimeDate());
                System.out.println("Blob Size (Bytes): " + fileUploadNotification.getBlobSizeInBytes());
                System.out.println("Enqueued Time: " + fileUploadNotification.getEnqueuedTimeUtcDate());
            }
            else
            {
                System.out.println("No file upload notification");
            }
    
            receiver.close();
        }
    
    }
    
  7. Salve e feche o my-app\src\main\java\com\mycompany\app\App.java arquivo.

  8. Use o seguinte comando para criar o aplicativo e verificar se há erros:

    mvn clean package -DskipTests
    

Executar a aplicação

Agora você está pronto para executar o aplicativo.

Em um prompt de my-app comando na pasta, execute o seguinte comando:

mvn exec:java -Dexec.mainClass="com.mycompany.app.App"

A captura de tela a seguir mostra a saída do aplicativo read-file-upload-notification :

Saída do aplicativo read-file-upload-notification

Próximos passos

Neste artigo, você aprendeu como usar o recurso de carregamento de arquivos do Hub IoT para simplificar o carregamento de arquivos de dispositivos. Pode continuar a explorar esta funcionalidade com os seguintes artigos:

Para explorar melhor os recursos do Hub IoT, consulte: